返回
从零开始,打造你的 Promise/A+ 实现
前端
2023-09-26 08:40:22
前言
Promise 是一种异步编程的解决方案,可以使我们的代码更简单整洁。它允许我们以同步的方式编写异步代码,避免了繁琐的回调嵌套。了解 Promise 原理可以帮助我们快速分析定位问题。今天,我们将从零开始,一步一步实现 Promise/A+ 规范。
理解 Promise/A+ 规范
Promise/A+ 规范定义了 Promise 的行为和实现要求。它确保了不同实现之间的互操作性,让我们可以放心地使用各种 Promise 库。规范规定了 Promise 的三个状态:Pending(等待)、Fulfilled(已完成)和 Rejected(已拒绝)。
实现 Promise
1. 状态管理
class Promise {
constructor(executor) {
this.state = 'pending';
this.result = undefined;
this.onFulfilledCallbacks = [];
this.onRejectedCallbacks = [];
executor(
(value) => this.resolve(value),
(reason) => this.reject(reason)
);
}
resolve(value) {
if (this.state !== 'pending') return;
this.state = 'fulfilled';
this.result = value;
this.onFulfilledCallbacks.forEach((callback) => callback(value));
}
reject(reason) {
if (this.state !== 'pending') return;
this.state = 'rejected';
this.result = reason;
this.onRejectedCallbacks.forEach((callback) => callback(reason));
}
}
2. then 方法
then(onFulfilled, onRejected) {
if (this.state === 'pending') {
this.onFulfilledCallbacks.push(onFulfilled);
this.onRejectedCallbacks.push(onRejected);
} else if (this.state === 'fulfilled') {
onFulfilled(this.result);
} else if (this.state === 'rejected') {
onRejected(this.result);
}
}
3. catch 方法
catch(onRejected) {
return this.then(undefined, onRejected);
}
4. 规范符合性测试
为了确保我们的 Promise 实现符合规范,我们可以使用以下测试用例:
const p1 = new Promise((resolve, reject) => {
setTimeout(() => {
resolve('成功');
}, 1000);
});
p1.then((result) => {
console.log(result); // '成功'
}).catch((reason) => {
console.log(reason); // 不会被调用
});
const p2 = new Promise((resolve, reject) => {
setTimeout(() => {
reject('失败');
}, 1000);
});
p2.then((result) => {
console.log(result); // 不会被调用
}).catch((reason) => {
console.log(reason); // '失败'
});
const p3 = new Promise((resolve, reject) => {
setTimeout(() => {
throw new Error('错误');
}, 1000);
});
p3.then((result) => {
console.log(result); // 不会被调用
}).catch((reason) => {
console.log(reason.message); // '错误'
});
结语
通过遵循 Promise/A+ 规范,我们可以实现一个可靠且灵活的 Promise。它允许我们以更简单、更优雅的方式编写异步代码,从而提高代码的可读性和可维护性。现在,我们已经掌握了 Promise 的原理,就可以自信地将它应用到我们的项目中了。
致谢
感谢 Promise/A+ 规范的贡献者,他们的工作为 JavaScript 中异步编程奠定了基础。