Skip to content

理解 JavaScript Promise 方法:all、race、any、allSettled

此文章是 FrontendMaster 上的 Advanced Web Development Quiz 課程筆記

問題

Connect the Promise methods to the right output

Match the answers to the correct options.

const promises = [
  new Promise((res) => setTimeout(() => res(1), 200)),
  new Promise((res) => setTimeout(() => res(2), 100)),
  new Promise((_, rej) => setTimeout(() => rej(3), 100)),
  new Promise((res) => setTimeout(() => res(4), 300)),
];
Promise[METHOD](promises)
  .then(res => console.log("Result:", res))
  .catch(e => console.log("Error:", e))
[1] all
[2] race
[3] any
[4] allSettled

[a] Result: 2
[b] Error: 3
[c] Result: [{...}, {...}, {...}, {...}]
[d] Result: 2

Promise

這題在比較 Promise.allPromise.racePromise.anyPromise.allSettled 的差異

這四個方法都可以傳入一個可以被迭代的參數,通常用陣列放一系列的 Promise,而回傳的值則各自有不同的結果,要依據情境來選擇適合的方法

Promise.all

參數中的所有 Promise 都會同時開始執行,並回傳一個 Promise 或空陣列

回傳一個 Promise,有以下幾種可能:

  • 已經 fulfilled:如果傳入的參數 (陣列)為空,會直接回傳一個空陣列
  • 非同步完成 (Asynchronously fulfilled):只要參數陣列內的所有 Promisefulfilled(如果任何參數不是 Promise 不影響結果),Promise.all() 會非同步地 fulfilled,並且該回傳的 fulfillment value 是一個包含所有 fulfillment values 的陣列,順序與傳入的 primise 順序相同,不受完成順序影響
  • 非同步拒絕 (Asynchronously rejected):只要「任何」參數陣列內的 Promise 出現 rejected,此時 Promise.all() 就會立刻 rejectrejection reason 會是第一個被 rejectedPromiserejection reason

用途:有一系列的 Promise 全部都必須成功拿到結果,但是不在意執行順序,一旦有任何錯誤就要執行錯誤處理

Promise.race

顧名思義,這是一個賽跑,目的是要取得第一個完成的結果,而且是不在乎他的結果是 resolvereject,最後都回傳一個 Promise

回傳一個 Promise,有以下幾種可能:

  • 傳入參數(陣列)如果不為空:則最後會回傳第一個有結果的 Promise,並且不在意結果是 resolvereject,如果其中有非同步的參數,那麼仍然會回傳 Promise
  • 傳入參數(陣列)如果為空:回傳的 Promise 會是一個永遠 pending 的狀態

用途:有一系列的 Promise,要同時執行,但只需要第一個最快執行完成的結果,結果可能是 resolvereject

Promise.any

Promise.race 有點像,差別在於 Promise.any 會優先回傳 resolvePromise

回傳一個 Promise,有以下幾種可能:

  • 已經 fulfilled:傳入參數(陣列)如果為空,立刻回傳一個包含 AggregateErrorrejection,它的 errors 會是空陣列
  • 非同步完成 (Asynchronously fulfilled):任一 promise fulfills 時,會非同步地 fullfilledfulfillment value 是第一個被 fulfilledpromise。而其他 promises 就會立刻被截斷。
  • 非同步拒絕 (Asynchronously rejected):當所有的 promisesreject 時,會非同步地 rejectedrejection reason 會是一個 AggregateError

用途:有一系列的 Promise 要同時執行,但只需要第一個最快執行完成且 fullfilled 的結果

Promise.allSettled

最後這個蠻實用的,會等所有的 Promise 都執行完成,一次回傳全部 Promise

回傳一個 Promise(沒有 "reject" ),有以下幾種可能:

  • 已經 fulfilled:傳入參數(iterable)為空時回傳此結果
  • 非同步完成 (Asynchronously fulfilled):參數(iterable)中 Promise 都完成時 (resolvereject 都可以),fulfillment value 會是一個物件陣列,每個物件代表每個 Promise 的結果,順序與傳入的 Promises 順序相同,不受完成順序影響。此物件包含以下屬性
    • status:字串;"fulfilled""rejected"
    • value:當 status 是 "fulfilled" 才會有這個值。包含 Promisefulfilled 的值
    • reason:當 status 是 "rejected" 才會有這個值。包含該 promise 被 rejected 的原因

即使傳入的參數(陣列)不為空但不包含任何 pending promises,回傳的 Promise 仍然會是非同步 fulfilled

用途:有一系列的 Promise 要同時執行,會不論執行結果全部回傳

答案

[1] [b]
[2] [d]
[3] [a]
[4] [c]

參考

最後更新時間:

0 %
MIT Licensed | Copyright © 2025-present Wen-Hsiu's Blog