代码实现
const PENDING = 'pending';
const RESOLVED = 'resolve';
const REJECTED = 'rejected';
function Promise (execute) {
const self = this;
self.status = PENDING;
self.value = undefined;
self.reason = undefined;
self.onFulfilledCallbacks = []
self.onRejectCallbacks = [];
function resolve (val) {
setTimeout(() => {
if (self.status === PENDING) {
self.status = RESOLVED;
self.value = val;
self.onFulfilledCallbacks.forEach(fn => fn());
}
}, 0)
}
function reject (reason) {
setTimeout(() => {
if (self.status === PENDING) {
self.status = REJECTED;
self.reason = reason;
self.onRejectCallbacks.forEach(fn => fn());
}
}, 0)
}
try {
execute(resolve, reject)
} catch (e) {
reject(e);
}
}
Promise.prototype.then = function (onFulfilled, onRejected) {
let self = this;
let promise2;
onFulfilled = typeof onFulfilled === 'function' ? onFulfilled : function (v) {
return v
};
onRejected = typeof onRejected === 'function' ? onRejected : err => {
throw err
};
return promise2 = new Promise((resolve, reject) => {
if (self.status === RESOLVED) {
setTimeout(() => {
try {
let x = onFulfilled(self.value);
promiseResolutionProcedure(promise2, x, resolve, reject);
} catch (err) {
return reject(err)
}
}, 0)
} else if (self.status === REJECTED) {
setTimeout(() => {
try {
let x = onRejected(self.reason);
promiseResolutionProcedure(promise2, x, resolve, reject)
} catch (err) {
return reject(err)
}
}, 0)
} else { // PENDING
self.onFulfilledCallbacks.push(() => {
setTimeout(() => {
try {
let x = onFulfilled(self.value);
promiseResolutionProcedure(promise2, x, resolve, reject)
} catch (e) {
reject(e)
}
}, 0)
})
self.onRejectCallbacks.push(() => {
setTimeout(() => {
try {
let x = onRejected(self.reason);
promiseResolutionProcedure(promise2, x, resolve, reject)
} catch (e) {
return reject(e)
}
}, 0)
})
}
})
}
function promiseResolutionProcedure (promise2, x, resolve, reject) {
if (promise2 === x) {
return reject(new TypeError('循环引用'));
}
let called;
if (x instanceof Promise) {
if (x.status === PENDING) {
x.then((val) => {
// resolve(val)
promiseResolutionProcedure(promise2, val, resolve, reject)
}, (e) => {
reject(e);
})
} else {
x.then(resolve, reject);
}
}
if (x != null && ((typeof x === 'function') || (typeof x === 'object'))) {
try {
let then = x.then;
if (typeof then === 'function') {
then.call(x, (y) => {
if (called) return;
called = true;
promiseResolutionProcedure(promise2, y, resolve, reject);
}, (err) => {
if (called) return;
called = true;
reject(err);
})
} else {
resolve(x);
}
} catch (e) {
if (called) return;
called = true;
reject(e);
}
}
else {
return resolve(x);
}
}
Promise.defer = Promise.deferred = function () {
let dfd = {};
dfd.promise = new Promise((resolve, reject) => {
dfd.resolve = resolve;
dfd.reject = reject;
});
return dfd;
}
module.exports = Promise;
var pro = new Promise((resolve, reject) => {
resolve(123)
})
pro.then(null, null).then(data => {
console.log(data)
})
promiseA+规范参考
https://promisesaplus.com/
Promise测试 脚本
1. 安装
npm install -g promises-aplus-tests
2. 测试
promises-aplus-tests promise.js