iT邦幫忙

第 12 屆 iT 邦幫忙鐵人賽

DAY 14
0
Modern Web

從ES到ESNext - 30天輕鬆掌握ECMAScript系列 第 14

[Day14] ES2015(ES6) - Promise

寫 ES5 時,只要需要寫到非同步請求,我們或多或少都有接觸到 promise 的寫法。但是因為在 Javascript 中還沒有實作,所以還要額外匯入支援的函式庫或模組,像是 jQueryBlueBird等。

ES2015 中,Promise 終於被納入標準。一直到現在,Promise 已經成為實作非同步方法中的基本方式。在 Fetch APIService Worker 等,主要也是以 Promise 實現非同步行為。所以今天就來好好認識吧!

Imgur

先來看 Promise 的執行流程。

  • 開始執行 Promise 物件,任務結束前的回傳,都會是 Pending 狀態
  • 任務結束後,如果沒發生意外錯誤,則會執行到 then()裡的 callback。反之則會執行到catch()裡的 Error handler
  • then 裡有兩個參數 resolvereject
    • 當任務結果成功,以resolve回傳,或在執行下個 then
    • 當任務結果失敗,以reject回傳

看個基本例子。

// 一秒後隨機取數,如果是偶數就會該數字,如果不是就回QQ
const p = new Promise((resolve, reject) => {
  setTimeout(() => {
    const n = Math.floor(Math.random() * 100);
    console.log(n);
    if (n % 2 == 0) resolve(n);
    else reject("QQ");
  }, 1000);
}).catch((err) => {
  console.error(err);
});

Promise.all([promise array])

同時完成多個 Promise。如果任務結束,且都無意外錯誤,就會執行then();反之則執行catch()處理錯誤。

const f1 = fetch("/a.json");
const f2 = fetch("/b.json");
Promise.all([f1, f2])
  .then(([r1, r2]) => {
    console.log("jsons:", r1, r2);
    // jsons: {...} {...}
  })
  .catch((err) => {
    console.error(err);
  });

Promise.race([promise array])

如同字面上意思,同時執行多個 Promise,只要最先完成 resolve 的,就會以這個 resolve 的結果執行 then()

const p1 = new Promise((resolve, reject) => {
  setTimeout(resolve, 200, "p1");
});
const p2 = new Promise((resolve, reject) => {
  setTimeout(resolve, 300, "p2");
});
Promise.race([p1, p2]).then((result) => {
  console.log(result); // p1
});

參考資源


上一篇
[Day13] ES2015(ES6) - 可迭代(Iterable)與產生器(Generator)
下一篇
[Day15] ES2015(ES6) - 模組 (Module)<未完>
系列文
從ES到ESNext - 30天輕鬆掌握ECMAScript30

尚未有邦友留言

立即登入留言