7

Introduction to Promise.race() and Promise.any() With Real-life Examples

 3 years ago
source link: https://blog.bitsrc.io/introduction-to-promise-race-and-promise-any-with-real-life-examples-9d8d1b9f8ec9
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

Introduction to Promise.race() and Promise.any() With Real-life Examples

Get an in-depth understanding of these two awesome methods

Image for post
Image for post
Photo by Ave Calvar on Unsplash

JavaScript has been steadily improving since its release in 1996. With many improvements coming in the form of ECMAScript versions, the most recent release being ES2020. You can read more about this release over here. I believe one of the prominent updates of JavaScript to be Promises, released in 2015 under the name ES6.

What is a Promise?

The MDN Docs defines a Promise as an object that represents the eventual completion (or failure) of an asynchronous operation and its resulting value. This might sound a bit too complicated for newbies.

Jecelyn explains Promises as follows: “Imagine you are a kid. Your mom promises you that she’ll get you a new phone next week.”

You won’t know if you will get that phone until next week. Your mom either really buys you a brand new phone — or she doesn’t because she is not happy.

That is a Promise. A Promise has three states. They are:

  1. Pending: You don’t know if you will get that phone.
  2. Fulfilled: Mom is happy and she buys you a brand new phone.
  3. Rejected: Mom is unhappy and she doesn’t buy you a phone.

This is by far the simplest and clearest explanation I’ve come across for Promises.

If you haven’t yet started learning promises, I would highly recommend you do so.

Promise contains several built-in methods which are very useful. We will be focusing mainly on two of these methods.

  • Promise.race() — released with ES6
  • Promise.any() — still in stage 4 proposal

Tip: Share your reusable components between projects using Bit (Github). Bit makes it simple to share, document, and organize independent components from any project.

Use it to maximize code reuse, collaborate on independent components, and build apps that scale.

Bit supports Node, TypeScript, React, Vue, Angular, and more.

Image for post
Image for post
Example: exploring reusable React components shared on Bit.dev

Promise.race()

The Promise.race() method was released initially with the introduction of Promises in ES6. This method expects an iterable as an argument. Promise.race() returns a Promise that settles as soon as one of the promises in the iterable argument settles. A settled Promise is simply a promise that either has resolved or rejected.

Unlike the Promise.any() method, which mainly considers whether a Promise has resolved, the Promise.race() method mainly focuses on whether a Promise has settled, regardless of it being resolved or rejected.

Syntax

Promise.race(iterable)

Parameters

  • iterable — an iterable object very similar to an array. Iterable objects implement the Symbol.iterator method. You can learn more about iterators here.

Return Value

A pending Promise that asynchronously returns the value of the first promise in the given iterable to settle.

Note

Since the parameter accepts an iterable, you can pass values such as primitive values and even objects within the array. In that case, the race method will return the first non-promise object that is passed. This is mainly because of the method’s behavior to return a value as soon as it’s available(when a promise settles).

Furthermore, if an already settled Promise is passed in the iterable, the Promise.race() method will resolve to the first of this value. If an empty iterable is passed, the race method will forever be in the pending state.

Code Example

Code Snippet by Author

In the above example, it can be clearly seen that even though there are several promises that have resolved, the Promise.race() method rejects with promise2 as it settles(rejects) earlier than the other two promises.

Real-Life Use Case

Now you might be wondering what you can do with the Promise.race() method. Well, the community uses this method for several use cases. Let’s have a look at them below.

  • Show a Loading Indicator When Server Response is Slow

Using a loading indicator is quite a common sight in web applications. Loading indicators are used when the data loading process takes a bit longer and the screen would look non-responsive if a loader is not used. But sometimes, it is acceptable to have a very small time margin before showing a loader. To achieve this, you can simply use the Promise.race() method as shown below.

Code Snippet by Michael Clark
  • Cancellable Promises

There might be instances where our promises would take forever to settle and we would be desperate for it to be canceled. You can create a function to cancel promises with the help of the Promise.race() method.

Code Snippet by Michael Clark
  • Batch Requests for Long-Running Execution

Chris Jensen had an interesting use case for the race() method. He had used the Promise.race() method to batch requests for a long-running execution. This allowed them to keep the number of parallel requests fixed and to add promises to the batch when one gets settled.

Code Snippet by Chris Jensen

Promise.any()

The Promise.any() method is still experimental and in stage 4. But being in stage 4 means that it is in the “Finished Proposals” stage and very much ready for release with an expected release date of 2021. Similar to the Promise.race() method, this method too expects an iterable as an argument.

The Promise.any() method will return a Promise that will resolve as soon as one of the promises in the iterable resolves or will reject if all of the promises in the iterable reject.

Unlike the Promise.race() method which focuses on the promise which settles the first, the Promise.any() method focuses on the promise which resolves the first.

Syntax

Promise.any(iterable)

Parameters

  • iterable — iterable object like arrays

Return Value

Things are a bit different here.

  • An already rejected Promise will be returned if the iterable is empty
  • An asynchronously resolved Promise if the iterable contains non-promise values
  • A pending Promise that resolves or rejects asynchronously when any of promises in the iterable resolve or if all the promises reject.

Note

When the Promise.any() method rejects, it will return an AggregateError object which is a sub class of the Error object. This aggregate error will contain an errors property with an array of rejection values.

Code Example

Code Snippet by Author

When you look at the above code, you will notice that the Promise.any() mainly concerns about the resolved value. It ignores promise1 which rejects at 100 milliseconds and considers the value of promise2 which resolves at 400 milliseconds.

Real-Life Use Case

  • Retrieve Resource From the Fastest Server

Users accessing your website can be from locations all around the globe. If your server is based on a single location, then the response time would differ for each user, based on their location. But if you have several servers, you can use the server which would yield the fastest response. In a situation like this, you can use the Promise.any() method to receive the response from the fastest server.

Code Snippet by Author

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK