• Async function, which is the syntactic sugar of the Generator function

Optimization and improvement

  1. Built-in actuator
  • Async functions are executed on one line, just like normal functions, unlike Generator functions that call the next method
  1. Better semantics
  • Async and await are semantic clearer than asterisks and yield. Async means that an asynchronous operation is taking place in a function, and await means that an expression immediately following it needs to wait for the result.
  1. Wider applicability.
  • The await command of async functions can be followed by Promise objects and primitive values (numeric, string, and Boolean values, but this is equivalent to synchronous operations)
  1. The return value is Promise
  • Async functions return a Promise object, which is much more convenient than Generator functions return an Iterator, and you can specify the next action using then methods

Conclusion:

  • Async functions can be thought of as multiple asynchronous operations wrapped in a Promise object, and await commands are syntactic sugar for internal THEN commands.

usage

  • An async function returns a Promise object, and you can use the then method to add a callback function. When the function executes, it will return as soon as an await is encountered, wait until the asynchronous operation is complete, and then execute the following statement in the function body
var fs = require('fs');
var readFile = function (fileName) {
    return new Promise(function (resolve, reject) {
        fs.readFile(fileName, function (error, data) {
            if (error) reject(error);
            resolve(data);
        });
    });
};
var asyncReadFile = async function () {
    var f1 = await readFile('./txt1.json');
    var f2 = await readFile('./txt2.json');
    console.log(f1.toString());
    console.log(f2.toString());
};
var result = asyncReadFile();
console.log(result);
Copy the code

grammar

  • Return Promise The sayNC function returns a Promise object that is returned by the return statement inside the async function and is used as an argument to the then method callback
Async function f() {return 'async function f'; } f().then(data => { console.log(data); // output an async function f})Copy the code
  • In the above code, the value returned by the return command inside f is received by the then callback.

Throw an error

  • An error is thrown inside the async function, which causes the returned Promise object to become reject. The thrown error object is received by the catch method callback.
Async function f2() {throw new Error(' test throw Error '); } f2().then(data => { console.log(data); }).catch(error => { console.log(error); // Error: test throws an Error})Copy the code

The state change of the Promise object

  • A Promise returned by an async function will not change its state until the Promise object behind the internal await command has finished executing, unless a return statement or an error is thrown. That is, the callback function specified by the THEN method is executed only after the asynchronous operation inside the async function is completed

Await orders

  • Normally, the await command is followed by a Promise object, and if it is not, it is converted to an immediately resolve Promise object
Async function f4() {return await 'not Promise'; } f4().then(data => { console.log(data); / / not Promise})Copy the code
  • In the code above, the argument to the await command is the string ‘not Promise’, which is converted to a Promise object and resolved immediately.
  • If the Promise object following the await command becomes reject, the reject argument is received by the catch callback.
Async function f5() {return await promise.reject (' error '); } f5().then(data => { console.log(data); }).catch(error => { console.log(error); / / error})Copy the code
  • Note: In this code, the await statement is preceded by no return, but the reject argument is still passed to the catch callback. The effect is the same if you say return before await
  • As soon as the Promise after an await statement changes to reject, the entire async function is interrupted.
Async function f6() {await promise.reject (' error '); Await promise.resolve (' correct '); } f6().then(data => {console.log(data); }).catch(error => { console.log(error); })Copy the code
  • In the above code, the second await statement will not be executed because the state of the first await statement changes to reject.
  • Sometimes we want to not interrupt the following asynchronous operation even if the previous asynchronous operation fails, and then we can put the first await in the try… Inside the catch structure, so that the second await is executed regardless of whether the asynchronous operation succeeds or not.
Async function f7() {try {await promise.reject (' error '); } catch {} return await promise.resolve (' correct '); }Copy the code
  • The alternative is to await a Promise object followed by a catch method to handle any errors that may occur earlier
Async function f8() {await promise.reject (' error '). Catch (error => {console.log(error); }); Return await promise.resolve (' correct '); }Copy the code
  • If an asynchronous operation following await fails, the Promise object returned by the async function is rejected.

Pay attention to the point

  • Await the Promise object after the await command, and the result may be rejected, so it is better to await the await command in the try… In the catch block
  • Asynchronous operations after multiple await commands, if there is no excitation relationship, it is better to let them all start at the same time;
let aw1 = await get1();
let aw2 = await get2();
let [aw1, aw2] = await Promise.all(get1(), get2());
Copy the code
  • The await command can only be used in async functions, and an error will be reported if it is in normal functions