背景

手写js的Promise

徐徐
前端
发表于 2026-04-14 16:00:00
🌺 摘要
手写一个js原生Promise

手动写一个Promise函数

const PENDING = "pending";
const FULFILLED = "fulfilled";
const REJECTED = "rejected";
class MyPromise {
  #state = PENDING;
  #result = undefined;
  #handlers = [];
  constructor(executor) {
    const resolve = (data) => {
      this.#changeState(FULFILLED, data);
    };
    const reject = (reason) => {
      this.#changeState(REJECTED, reason);
    };
    try {
      executor(resolve, reject);
    } catch (error) {
      reject(error);
    }
  }
  #isPromiseLike(value) {
    if (
      value !== null &&
      (typeof value === "object" || typeof value === "function")
    )
      return typeof value.then === "function";
    return false;
  }
  #changeState(state, result) {
    if (this.#state !== PENDING) return;
    this.#state = state;
    this.#result = result;
    this.#run();
  }
  #runMicoTask(callback) {
    if (typeof queueMicrotask !== "function") {
      queueMicrotask(callback);
    } else if (
      typeof process === "object" &&
      typeof process.nextTick === "function"
    ) {
      process.nextTick(callback);
    } else if (typeof MutationObserver === "function") {
      const ob = new MutationObserver(callback);
      const textNode = document.createTextNode("1");
      ob.observe(textNode, {
        characterData: true,
      });
      textNode.data = "2";
    } else {
      setTimeout(callback, 0);
    }
  }
  #run() {
    if (this.#state === PENDING) return;
    while (this.#handlers.length) {
      const { onFulfilled, onRejected, resolve, reject } =
        this.#handlers.shift();
      if (this.#state === FULFILLED) {
        this.#runOne(onFulfilled, resolve, reject);
      } else {
        this.#runOne(onRejected, resolve, reject);
      }
    }
  }
  #runOne(callback, resolve, reject) {
    this.#runMicoTask(() => {
      if (typeof callback !== "function") {
        const settled = this.#state === FULFILLED ? resolve : reject;
        settled(this.#result);
        return;
      }
      try {
        const data = callback(this.#result);
        if (this.#isPromiseLike(data)) {
          data.then(resolve, reject);
        } else {
          resolve(data);
        }
      } catch (error) {
        reject(error);
      }
    });
  }
  then(onFulfilled, onRejected) {
    return new MyPromise((resolve, reject) => {
      this.#handlers.push({
        onFulfilled,
        onRejected,
        resolve,
        reject,
      });
      this.#run();
    });
  }
}
function test() {
  return new MyPromise((resolve, reject) => {
    reject(1);
  });
}
async function test1() {
  try {
    const a = await test();
    console.log(a, "===a");
  } catch (error) {
    console.log(error, "==e");
  }
}
test1();
文章发表于 2026-04-14 16:00:00
作者:徐徐
转载请注明出处
上一篇:微队列的几种实现方法
下一篇:js伪数组