有关promise的实现,首先需要了解promise是如何使用的,需要对promise的调用关系很熟悉。
第一版,实现了then方法,以及resolve,reject等,关于promise 内部状态的改变,抛出异常后的处理,以及链式调用then方法的处理方式。
class MaoPromise {
static _PROMISE_STATUS_PENDING = "pending";
static _PROMISE_STATUS_FULFILLED = "fulfilled";
static _PROMISE_STATUS_REJECTED = "rejected";
_status = MaoPromise._PROMISE_STATUS_PENDING;
_value = undefined;
_reason = undefined;
_onFulfilledCallback = [];
_onRejectedCallback = [];
constructor(executor) {
try {
executor(this.resolve, this.reject);
} catch (err) {
this.reject(err);
}
}
resolve = (value) => {
if (this._status === MaoPromise._PROMISE_STATUS_PENDING) {
queueMicrotask(() => {
if (this._status !== MaoPromise._PROMISE_STATUS_PENDING) return;
this._value = value;
this._status = MaoPromise._PROMISE_STATUS_FULFILLED;
this._onFulfilledCallback.forEach(callback => {
callback(this._value);
});
});
}
}
reject = (reason) => {
if (this._status === MaoPromise._PROMISE_STATUS_PENDING) {
queueMicrotask(() => {
if (this._status !== MaoPromise._PROMISE_STATUS_PENDING) return;
this._reason = reason;
this._status = MaoPromise._PROMISE_STATUS_REJECTED;
this._onRejectedCallback.forEach(callback => {
callback(this._reason);
});
});
}
}
then(onFulfilled, onRejected) {
return new MaoPromise((resolve, reject) => {
if (this._status === MaoPromise._PROMISE_STATUS_FULFILLED) {
if (typeof onFulfilled === "function") {
this._executorFunctionWithCatchError(onFulfilled, this._value, resolve, reject);
}
}
else if (this._status === MaoPromise._PROMISE_STATUS_REJECTED) {
if (typeof onRejected === "function") {
this._executorFunctionWithCatchError(onRejected, this._reason, resolve, reject);
}
}
if (typeof onFulfilled === "function")
this._onFulfilledCallback.push(() => {
this._executorFunctionWithCatchError(onFulfilled, this._value, resolve, reject);
});
if (typeof onRejected === "function")
this._onRejectedCallback.push(() => {
this._executorFunctionWithCatchError(onRejected, this._reason, resolve, reject);
});
});
}
_executorFunctionWithCatchError(execFn, value, resolve, reject) {
try {
const res = execFn(value);
resolve(res);
} catch (err) {
reject(err);
}
}
}
const promise = new MaoPromise((resolve, reject) => {
resolve("111");
});
promise.then((res) => {
console.log(res);
return "asa";
}, err => {
console.log(err.message);
}).then(res => {
console.log(res);
})