What are the differences between Promise.all() and Promise.allSettled()?

Asked

Viewed 4,239 times

11

I’m running some tests with Promises and I found that there are two ways to get the result of a set of protocols:

using Promise.all():

async searchSegmentsInformations(segmentId) {
    try {
      const segment = await Segment.find(segmentId);
      return segment;
    } catch (error) {
      throw new Error(error);
    }
  }

  testePromises() {
    const segmentsIds = [
      { id: 'bd84f021-30fb-4dad-b21a-6d673610db93' },
      { id: '25fcd038-58c2-44c2-aa9b-43529d591ed3' },
      { id: 'e1e9fd46-63ad-4ad9-af85-a16bd71a5b22' },
      { id: 'ca9f3a88-cb91-465a-87be-0c4bcfefa299' }
    ];

    const teste = Promise.all(
      segmentsIds.map((s) => this.searchSegmentsInformations(s.id))
    )
      .then((result) => {
        return result
      })
      .catch((error) => {
        console.log(error);
      });

    return teste;
  }

with Promise.allSettled():

async searchSegmentsInformations(segmentId) {
    try {
      const segment = await Segment.find(segmentId);
      return segment;
    } catch (error) {
      throw new Error(error);
    }
  }

  testePromises() {
    const segmentsIds = [
      { id: 'bd84f021-30fb-4dad-b21a-6d673610db93' },
      { id: '25fcd038-58c2-44c2-aa9b-43529d591ed3' },
      { id: 'e1e9fd46-63ad-4ad9-af85-a16bd71a5b22' },
      { id: 'ca9f3a88-cb91-465a-87be-0c4bcfefa299' }
    ];

    const teste = Promise.allSettled(
      segmentsIds.map((s) => this.searchSegmentsInformations(s.id))
    )
      .then((result) => {
        const segmentsInformations = result.map((r) => r.value);
        return segmentsInformations;
      })
      .catch((error) => {
        console.log(error);
      });

    return teste;
  }

What’s the difference between the two?
Both have the same compatibility?
When I should wear one or the other?

1 answer

13


Basically, Promise.all and Promise.allSettled are two between the so-called "promise combinators". In summary, Promise.all will return a array with the result values of all past promises. He will reject if any of them fail. Now Promise.allSettled return a list with information relating to all past promises, no matter if they have been resolved or rejected.

Promise.all

The function Promise.all gets a array of Promises and executes them in "parallel". If all past promises have been resolved, this method will return a new one array with the resolution value of all of them. If one of them fails, Promise.all will make a "short circuit", so it will reject with the reason of failure of the first of them.

Promise.all was introduced with the Ecmascript 2015 (ES6) standard. So if the environment you are using supports Promise, will support, in theory, Promise.all also, since both were standardized in the same specification.

Take an example:

const promises = [
  Promise.resolve(1),
  Promise.resolve(2),
  Promise.resolve(3),
];

Promise.all(promises)
  .then((list) => {
    console.log('Result:');
    console.log(list);
  })
  .catch((error) => {
    console.log('Error:');
    console.log(error);
  });

Now note that if one of the past promises fails, Promise.all also reject, with the reason of the first failure:

const promises = [
  Promise.resolve(1),
  Promise.reject('Eu vou falhar e arruinar tudo.'),
  Promise.resolve(3),
];

Promise.all(promises)
  .then((list) => {
    console.log('Result:');
    console.log(list);
  })
  .catch((error) => {
    console.log('Error:');
    console.log(error);
  });

Promise.allSettled

The method Promise.allSettled, similarly to Promise.all, also receives a array of promises, running them in "parallel". However, it returns a array of objects, describing the result of the promise. This object has two properties:

  • status, which indicates the result of the promise. It can take fulfilled in the case of the resolution of the promise, or reject in the event of its rejection;
  • value, the value of the outcome of the promise.

Therefore, Promise.allSettled will be resolved only after all as Promisethe past has a result and may be negative(s) or positive(s).

Take an example:

const promises = [
  Promise.resolve(1),
  Promise.reject('Eu vou falhas, mas NÃO vou arruinar tudo.'),
  Promise.resolve(3),
];

Promise.allSettled(promises)
  .then((list) => {
    console.log('Result:');
    console.log(list);
  })
  .catch((error) => {
    console.log('Error:');
    console.log(error);
  });

The method Promise.allSettled, unlike Promise.all, is much more recent. It was introduced in Ecmascript 2020. See support table to see if your environment supports this method before using it.

Completion

If for some reason you want to perform some action if a task list is executed with 100% success, use Promise.all, that will guarantee you that.

If you need to run a full list of promises, no matter if they have been resolved or rejected, Promise.allSettled will be your friend.

See the links for the answer to deepening.

Browser other questions tagged

You are not signed in. Login or sign up in order to post.