1024programmer JavaScript Detailed explanation of Promise and Async in JS

Detailed explanation of Promise and Async in JS

Because Javascript is a single-threaded language, synchronous code executes only one line at a time. This means that if the synchronous code runs for more than an instant, it will stop the rest of the code from running until it finishes running. To prevent code with an indeterminate runtime from blocking other code from running, we need to use asynchronous code.

Promise

For this, we can use Promise in our code. A Promise represents an object whose process runs for an indeterminate time and may result in success or failure. To create a promise in Javascript, we use the constructor of the Promise object to create the promise. The Promise constructor accepts a fulfillment function with resolve and reject parameters. Both parameters are also functions, which allow us to call back the promise fulfillment (successful call gets a return value) or rejection (returns an error value and marks the promise as failed). The return value of the function is ignored. Therefore, promises can only return promises.

For example, we define a promise in Javascript like the following code:

const promise = new Promise((resolve, reject) =  > {
   setTimeout(() => resolve('abc'), 1000);
 });

The code above creates a promise that returns abc after one second. Because we run setTimeout that returns a fulfilled promise with value abc after one second inside the executor function, it’s asynchronous code. We cannot return the value abc in the callback function of setTimeout, so we have to call resolve('abc') to get the resolved value. We can use the then function to access the return value of the fulfilled promise. The then function accepts a callback function that takes the return value of the fulfilled promise as an argument. You can get the value you want. For example, we can do this:

const promise = new Promise((resolve, reject) => {
   setTimeout(() => resolve('abc'), 1000);
 });
 promise. then((val) => {
   console. log(val);
 })

When we run the above code, we should get record abc. As we can see, a promise provides a value when the resolve function is called after its fulfillment.

A promise has three states. In the initial state, the promise neither succeeds nor fails. Completion status, meaning the operation completed successfully. Or a failed state, meaning the promise operation failed.

A pending promise can either be fulfilled by returning a value or fail with an error. When the promise is fulfilled, the then function will get the corresponding return value and pass it to the callback function of the then function to call. If the promise fails, we can choose to use the catch function to catch the error, which can also pass an error to the callback function. Both then and catch return a promise, so they can be chained together.

For example, we can write:

const promise = (num) => {
   return new Promise((resolve, reject) => {
     setTimeout(() => {
       if (num === 1) {
         resolve('resolved')
       } else {
         reject('rejected')
       }
     }, 1000);
   });
 }
 promise(1)
   .then((val) => {
     console. log(val);
   })
   .catch((error) => {
     console. log(error);
   })promise(2)
   .then((val) => {
     console. log(val);
   })
   .catch((error) => {
     console. log(error);
   })

In the code above, we have a function promise that returns a Javascript promise that fulfills the promise with the resolved value when num is 1 and rejects the promise with the error rejected when num is not 1 . So we run:

promise(1)
   .then((val) => {
     console. log(val);
   })
   .catch((error) => {
     console. log(error);
   })

then the then function runs, and since num is 1, the promise(1) function call returns that the promise fulfills and the resolved value is available in val. So when we run console.log(val), we get resolved. When we run the following code:

promise(2)
   .then((val) => {
     console. log(val);
   })
   .catch((error) => {
     console. log(error);
   })

catch will run because a promise(2) function call fails to return a promise, and the rejected error value is available and set to error. So we run console.log(error) and get rejected output.

A Javascript promise object has the following properties: length and prototype. length is the number of constructor parameters, which is set to 1, and there is always only one. The prototype property represents the prototype of the promise object.

promise also has a finally method that runs code whether the promise completes or fails. The finally method accepts a callback function as a parameter, which can run any code you want to run, and it can be executed regardless of the result of the promise. For example, we run:

Promise.reject('error')
   .then((value) => {
     console. log(value);
   })
   .catch((error) => {
     console. log(error);
   })
   .finally(() =We replace the object passed into then with the inject function, and we get the rejected promise.  The code is as follows:

Promise.resolve({
     then(resolve, reject) {
       reject('error');
     }
   })
   .then((value) => {
     console. log(value);
   })
   .catch((error) => {
     console. log(error);
   })

In the above code, we will get an error log because the promise was rejected.

Async and Await

Using async and await, we can shorten the promise code. Before using async and await, we have to use then function and put callback function as all parameters in then function. This makes our code extremely verbose when we have many promises. Instead, we can use async and await syntax instead of then functions and associated callbacks. For example, we can shorten the following code to:

const promise1 = new Promise((resolve, reject) => {
   setTimeout(() => resolve(1), 2000);
 });
 const promise2 = new Promise((resolve, reject) => {
   setTimeout(() => resolve(2), 1000);
 });
 promise1
   .then((val1) => {
     console. log(val1);
     return promise2;
   })
   .then((val2) => {
     console. log(val2);
   })

Written as:

const promise1 = new Promise((resolve, reject) => {
   setTimeout(() => resolve(1), 2000);
 });
 const promise2 = new Promise((resolve, reject) => {
   setTimeout(() => resolve(2), 1000);
 });
 (async () => {
   const val1 = await promise1;
   console. log(val1)
   const val2 = await promise2;
   console. log(val2)
 })()

We use await to replace then and callback functions. We can then assign the resolved value of each promise as a variable. Note that if we use await for the promise code, then we have to add async to the function signature as in the example above. To catch errors, we use a catch clause instead of chaining catch functions. Also, instead of chaining finally functions at the bottom to run code when the promise ends, we use a finally clause after the catch clause.

For example, we can write like this:

const promise1 = new Promise((resolve, reject) => {
   setTimeout(() => resolve(1), 2000);
 });
 const promise2 = new Promise((resolve, reject) => {
   setTimeout(() => reject('error'), 1000);
 });
 (async () => {
   try {
     const val1 = await promise1;
     console. log(val1)
     const val2 = await promise2;
     console. log(val2)
   } catch (error) {
     console. log(error)
   } finally {
     console.log('finally runs');
   }})()

In the code above, we get the resolved value of the promise assigned to the variable instead of getting the value in the callback of the then function, for example in const respOnse= await promise1 above one line. Additionally, we use try...catch...finally blocks to catch errors for rejected promises, and finally clauses instead of finally functions, which allow the code to run regardless of the outcome of the promise.

Like other functions that use promises, async functions always return promises and cannot return anything else. In the example above, we demonstrated that we can use promises in a shorter way than using a then function with a callback function passed as an argument.

Conclusion

Using promises makes it easier for us to write asynchronous code. A promise is an object that represents a process whose runtime is indeterminate and whose outcome will either succeed or fail. To create a promise in Javascript, we use the Promise object which is the constructor used to create the promise.

The Promise constructor accepts an execute function with resolve and reject parameters. Both arguments are functions that allow us to call back promise fulfillment (successful call with return value) or rejection (return error value and flag promise failure). The return value of the function is ignored. Therefore, promises can only return promises.

Because promises return promises, promises are chainable. A promise's then function can throw an error, return a resolved value, or another promise (pending, fulfilled, or rejected promises).

Recommended tutorial: "PHP Tutorial"

The above is the detailed content of Promise and Async in JS. For more, please pay attention to other related articles on 1024programmer.com!

This article is from the internet and does not represent1024programmerPosition, please indicate the source when reprinting:https://www.1024programmer.com/detailed-explanation-of-promise-and-async-in-js/

author: admin

Previous article
Next article

Leave a Reply

Your email address will not be published. Required fields are marked *

Contact Us

Contact us

181-3619-1160

Online consultation: QQ交谈

E-mail: [email protected]

Working hours: Monday to Friday, 9:00-17:30, holidays off

Follow wechat
Scan wechat and follow us

Scan wechat and follow us

Follow Weibo
Back to top
首页
微信
电话
搜索