手写Promise - 实现一个根底的Promise
手写Promise - 实例办法catch、finally
手写Promise - 罕用静态方法all、any、resolve、reject、race
上一篇文章手写了一个根底的Promise,咱们持续来欠缺它,为其增加常常用到的catch和finally办法
catch & finally
catch() 办法返回一个Promise,并且解决回绝的状况。咱们晓得then办法的第二个参数其实就是干这个用的,catch只是一个别名。
finally() 办法返回一个Promise。在promise完结时,无论后果是fulfilled或者是rejected,都会执行指定的回调函数。和catch一样,也只是对then的一个简写,相当于是传入的函数既是onFulfilled也是onRejected。
有一点须要留神,finally和catch办法只是then的一个别名,实际上返回的还是一个promise,齐全能够这样写:promise.then().finally().then().catch().then()
咱们把上一章节的代码拷过去,而后向外面增加catch和finally办法。
class WPromise { static pending = 'pending'; static fulfilled = 'fulfilled'; static rejected = 'rejected'; constructor(executor) { this.status = WPromise.pending; // 初始化状态为pending this.value = undefined; // 存储 this._resolve 即操作胜利 返回的值 this.reason = undefined; // 存储 this._reject 即操作失败 返回的值 // 存储then中传入的参数 // 至于为什么是数组呢?因为同一个Promise的then办法能够调用屡次 this.callbacks = []; executor(this._resolve.bind(this), this._reject.bind(this)); } // onFulfilled 是胜利时执行的函数 // onRejected 是失败时执行的函数 then(onFulfilled, onRejected) { // 返回一个新的Promise return new WPromise((nextResolve, nextReject) => { // 这里之所以把下一个Promsie的resolve函数和reject函数也存在callback中 // 是为了将onFulfilled的执行后果通过nextResolve传入到下一个Promise作为它的value值 this._handler({ nextResolve, nextReject, onFulfilled, onRejected }); }); } // catch办法只有一个参数用于处理错误的状况 catch(onRejected) { return this.then(null, onRejected); } finally(onFinally) { return this.then(onFinally, onFinally); } _resolve(value) { // 解决onFulfilled执行后果是一个Promise时的状况 // 这里可能了解起来有点艰难 // 当value instanof WPromise时,阐明以后Promise必定不会是第一个Promise // 而是后续then办法返回的Promise(第二个Promise) // 咱们要获取的是value中的value值(有点绕,value是个promise时,那么外部存有个value的变量) // 怎么将value的value值获取到呢,能够将传递一个函数作为value.then的onFulfilled参数 // 那么在value的外部则会执行这个函数,咱们只须要将以后Promise的value值赋值为value的value即可 if (value instanceof WPromise) { value.then( this._resolve.bind(this), this._reject.bind(this) ); return; } this.value = value; this.status = WPromise.fulfilled; // 将状态设置为胜利 // 告诉事件执行 this.callbacks.forEach(cb => this._handler(cb)); } _reject(reason) { if (reason instanceof WPromise) { reason.then( this._resolve.bind(this), this._reject.bind(this) ); return; } this.reason = reason; this.status = WPromise.rejected; // 将状态设置为失败 this.callbacks.forEach(cb => this._handler(cb)); } _handler(callback) { const { onFulfilled, onRejected, nextResolve, nextReject } = callback; if (this.status === WPromise.pending) { this.callbacks.push(callback); return; } if (this.status === WPromise.fulfilled) { // 传入存储的值 // 未传入onFulfilled时,将undefined传入 const nextValue = onFulfilled ? onFulfilled(this.value) : undefined; nextResolve(nextValue); return; } if (this.status === WPromise.rejected) { // 传入存储的错误信息 // 同样的解决 const nextReason = onRejected ? onRejected(this.reason) : undefined; nextReject(nextReason); } }}
是的,就是这么简略,当初来测试一下:
function fetchData() { return new WPromise((resolve, reject) => { setTimeout(() => { reject(1); }, 1000); });}fetchData().finally((data) => { return data + 10;}).finally((data) => { return new WPromise((resolve, reject) => { reject(data + 10); });}).finally((data) => { console.log(data); // 21})
以上就是catch和finally的模仿实现,如果了解了then的工作原理的话,了解catch和finally也没啥问题。