Understanding of JS, Promise,async/await
A, js
const a = function() {
setTimeout(function() {
console.log(1)},2000)
}
a()
console.log(2)
// Execution result:
2
1
Copy the code
SetTimeout simulates asynchronous callback functions, assuming that a callback takes 2 seconds to guess the return result. You can see that when the a function is called, the next line of print is executed without immediately printing the result. Js is single-threaded and executes statements from top to bottom, with a callback mechanism in order not to block statement execution. A callback registers a pool of events into which the callback function executes its own logic and returns results to the main thread. The following node connects to the database and returns undefined.
var mysql = require('mysql'); Const mysql = function() {console.log(' connected database is ', database) const url = {host: 'localhost', user: 'root', password : '123456', database : 'test' } var connection = mysql.createConnection(url); connection.connect(); var mysqlQuery = function(callback) { var sql = 'SELECT * FROM test1' connection.query(sql,function(err,result){ if(err){console.log(err)} callback(result) }) } const result = mysqlQuery(function(data) { return data }) Console. log(result) console.log(2)} mysql() // Can not get the result when console.log(result)Copy the code
Second, the promise
The callback function of the promise state changes into then and catch, (can also be placed in then). If the promise succeeds, then functions will be executed, and if the promise fails, catch functions will be executed. We can execute which callbacks we want and easily control the order in which they are executed. The Promise constructor takes resolve and reject. Resolve changes the state of the Promise object from pending to Resolved. The reject function changes the state of a Promise object from Pending to Reject. Callbacks to state changes are defined in then.
// Instantiate the Promise object. What about the constructor for the promise object
const promise = new Promise(function(resolve, reject) {
// ... some code
if (/* Asynchronous operation succeeded */){
resolve(value);
} else{ reject(error); }});// After the Promise instance is generated, you can use the THEN method to specify the Resolved and Rejected state callback functions, respectively.
promise.then(function(value) {
// success
}, function(error) {
// failure
})
Copy the code
After the Promise instance is created, the state-changed callback will not be executed until all synchronization tasks in the current script have been completed.
let promise = new Promise(function(resolve, reject) {
console.log('Promise');
resolve();
});
promise.then(function() {
console.log('resolved.');
});
console.log('Hi! ');
// Promise
// Hi!
// resolved`
Copy the code
In the code above, the Promise is executed immediately after it is created, so the Promise is printed first. Then, the callback specified by the then method will not execute until all synchronization tasks in the current script have finished, so resolved will output.
Third, ansyc/await
Async
Start with the async keyword, which is placed in front of a function. Like this:
async function f() {
return1}Copy the code
The async word in front of the function implies a simple thing: the function always returns a promise, and if there is a return < non-promise > statement in the code, JavaScript will automatically wrap the returned value as the Promise resolved value. Then (reslove) gets the value of return
async function f() {
return 1
}
f().then(alert) // 1
Copy the code
You can explicitly return a promise, which will have the same result:
async function f() {
return Promise.resolve(1)
}
f().then(alert) // 1
Copy the code
Await
// Can only be used inside async functionslet value = await promise
Copy the code
The keyword await makes JavaScript wait until a promise executes and returns its result. Example:
async function f() {
let promise = new Promise((resolve, reject) => {
setTimeout(() => resolve('done! '), 1000)})letResult = await promise // until promise returns a resolve value (*) alert(result) //'done! '
}
f()
Copy the code
The function will ‘pause’ on the (*) line and resume execution after the promise processing is complete. Await will return the result of the promise execution, assigned to result, resolve will be the final result, so the code above will print ‘done! ‘. Await is a more elegant statement to get a promise and is easier to read and write than a promise. That is, replace the.then of the promise with await
- Await cannot work in top-level scope
let response = await fetch('/article/promise-chaining/user.json') let user = await response.json() So we need to wrap the await code in an async function, as in the example above.Copy the code
- A class method can also use async by placing async before it like this:
Async wait() {return await promise.resolve (1)}} new Waiter().wait().then(alert) // 1 It ensures that the return value is a promise and supports awaitCopy the code
Error handling
If a promise is normal resolve, await returns the result, but reject throws an error as if there were a throw statement on that line.
async function f() {
await Promise.reject(new Error('whoops! '))}Copy the code
Same thing as below
async function f() {
throw new Error('Whoops! ')}Copy the code
In a real-world usage scenario, a promise might take some time before reject throws an error, so await would wait before throwing an error. We can use try-catch statements to catch errors just as we would handle exceptions in a normal throw:
async function f() {
try {
let response = await fetch('http://no-such-url')
} catch (err) {
alet(err) // TypeError: failed to fetch
}
}
f()
Copy the code
If we do not use a try-catch and then async f() produces a reject promise, we can add a. Catch to handle it:
async function f() {
let response = await fetch('http://no-such-url'} // f() is a rejected promise f(). Catch (alert) // TypeError: failed to fetchCopy the code
Async /await can work nicely with promise.all. When we need to wait for multiple promises, we can wrap them in promise.all and use await: // until the array has all returned resultsletresults = await Promise.all([ fetch(url1), fetch(url2), ... ] ) If an error occurs, it goes from a failed state promise to promise.all, which then becomes an exception that we can catch using try-CATHc.Copy the code
See article async/await
4. Modify the asynchronous callback example in JS
var mysql = require('mysql'); Const mysql = function() {console.log(' connected database is ', database) const url = {host: 'localhost', user: 'root', password : '123456', database : 'test' } var connection = mysql.createConnection(url); connection.connect(); var mysqlQuery = new Promise((resolve, reject) => { var sql = 'SELECT * FROM test1' connection.query(sql,function(err,result){ if(err){console.log(err)} resolve(result) }) }) const result = await mysqlQuery(function(data) { return data }) console.log(result) console.log(2) } mysql(); // mysql()Copy the code