Fehler in Promise.all abfangen

Eine sichere Alternative zu Javascripts Promise.all

Warten auf alle Versprechen, einschließlich Fehler

Wenn Sie ein Javascript-Entwickler sind, haben Sie höchstwahrscheinlich das integrierte Standardobjekt Promise und seine API Promise.all verwendet, die wartet, bis alle in einem Array bereitgestellten Promises aufgelöst wurden. Dies ist eine sehr elegante Möglichkeit, verschiedene asynchrone Ergebnisse abzuwarten, bevor Sie mit Ihrer Geschäftslogik fortfahren.

Aber diese API behandelt keine Fehler. Wenn mindestens ein Fehler im Array von Promises auftritt, wird die Funktion sofort beendet und es werden keine weiteren Ergebnisse erwartet.

Promise.allSettled erwartet alle asynchronen Ergebnisse

Zum Glück gibt es eine zweite API namens Promise.allSettled, die garantiert, auf alle Versprechen zu warten, egal ob das Ergebnis gültig oder ein Fehler ist. Der folgende Code demonstriert seine Verwendung, die wirklich einfach ist, Ihnen aber viel Kopfzerbrechen ersparen kann.

Der Hauptunterschied zu Promise.all besteht darin, dass jedes Versprechen in ein Informationstupel aufgelöst wird, in dem sowohl der Zustand (erfüllt oder abgelehnt) als auch der Wert (bei Erfüllung) oder der Grund (bei Ablehnung) verfügbar sind .

Bereitstellen eines leeren Arrays

Ein besonderer Fall, den Sie beachten sollten, ist, dass Promise.allSettled, wenn er ein leeres Array als Eingabe erhält, sofort in ein leeres Array umgewandelt wird. Das klingt logisch und ist das erwartete Verhalten, aber ich wollte trotzdem darauf hinweisen.

/**
 * A simple dummy function that
 * fetches data from multiple
 * endpoints related to a user.
 */
async function fetchUserData(id){
  // A simple array of promises.
  // The first two parameters are
  // mock calls from down below.
  const promises = [
    fetchUserHistory(id),
    fetchUserProfile(id),
    // For testing only, let's throw.
    Promise.reject(new Error('an error'))
];
  
  const values = await Promise.allSettled(promises);
  // values === [
  //    { status: "fulfilled", value: [1, 2, 3] },
  //    { status: "fulfilled", value: {name:"dummy"} },
  //    { status: "rejected", reason: {}
  // ]
}

// The following functions are just mocks
// and should help improve readability
// of the example at the top.

async function fetchUserHistory(id){
  return Promise.resolve([1,2,3]);
}

async function fetchUserProfile(id){
  return Promise.resolve({ name: "dummy" });
}

Wie Sie sehen, ist Promise.allSettled eine sehr schöne Ergänzung zu Promise.all und ermöglicht es Ihnen, alle Ergebnisse unabhängig von ihren Ergebnissen abzuwarten. Ich glaube nicht, dass diese API für jeden Anwendungsfall geeignet ist, aber sie erspart Ihnen das Einwickeln asynchroner Aufrufe in einen Overhead-Try-Catch-Block.