AsyncSeriesHook
AsyncSeriesHook 钩子函数实现的是串行任务,每个任务返回值都是promise, 它能实现先添加的任务先执行,并且前一个任务要成功resolve,才执行后一个任务,所有任务都resolve后执行最终的then()回调
现在来模拟一下
要执行的任务代码
tap(){
// 订阅消息
this.hooks.vue.tapPromise("zs", (des) => {
return new Promise(function (resolve, reject) {
setTimeout(function () {
console.log("zs", des);
resolve();
}, 3000);
})
});
this.hooks.vue.tapPromise("ls", function (des, cb) {
return new Promise(function (resolve, reject) {
setTimeout(function () {
console.log("ls", des);
resolve();
}, 2000);
})
});
this.hooks.vue.tapPromise("ww", function (des, cb) {
return new Promise(function (resolve, reject) {
setTimeout(function () {
console.log("ww", des);
resolve();
}, 1000);
})
});
}
call(){
// 发布消息
this.hooks.vue.promise("vue课程上线了").then(function () {
console.log("end");
});
}
执行这个任务
promise(...args){
if(args.length < this.args.length){
return new Error("参数个数不对");
}
args = args.slice(0, this.args.length + 1);
let [firstTask, ...others] = this.tasks;
//核心工具reduce
return others.reduce(function (promise, task) {
return promise.then(()=>{
return task(...args);
});
}, firstTask(...args));
}
这里用到的es6的reduce()函数,核心代码就是这个reduce,现在来分析一下整个reduce的执行过程
首先对promise的返回值与promise的嵌套搞了一个demo
//Promise.resolve() 返回值也是promise, [[PromiseState]]: "fulfilled", [[PromiseResult]]: "hello"
//Promise.resolve().then() 返回值也是promise, [[PromiseState]]: "fulfilled", [[PromiseResult]]: "hello"
// let res = Promise.resolve('hello').then()
// console.log(res)
let myPromise = new Promise((resolve, reject) => {
resolve('myPromise')
})
//这里更容易看出, myPromise.then()返回的是一个Promise
//如果没有resolve, 打印[[PromiseState]]: "pending", [[PromiseResult]]: undefined
//如果resolve()了,则打印[[PromiseState]]: "fulfilled", [[PromiseResult]]: undefined
let newPromise = new Promise((resolve, reject) => {
resolve('newPromise')
})
let res = myPromise.then((val) => {
//return val
//这里能明显看出,如果return val则返回的res是myPromse这个实例
//如果内部再返回一个newPromise,则返回的res是这个内部的newPromise实例
return newPromise
})
console.log(res)
分析上边核心代码reduce()的执行流程
//这里分析firstTasks(...args),如果这个promise没有resolve,则这个promise作为最终的返回值返回给外界 ress,输出'zs'
//如果resolve了,则执行then(),这时firstTasks(...args)返回的promise就不作为最终的返回值返回给外界ress了
//执行then() 则输出 'i am resolved',然后return 第二个任务的promise,现在情况是外层是第一个promise,内层返回了第二个promise
//当两个promise嵌套的时候会返回内层的promise,见以上demo分析
//现在的情况是这个内层的promise去哪了?
//1 返回给外界ress, 2 赋值给promiset
//猜测是赋值给promiset, 这是reduce正常迭代过程,输出 'ls'
//分析 如果这个promiset 没有 resolve ,则第二个promise直接返回给外界了
//如果这个promiset resolve 了,则 输出 'i am resolved',然后把第三个promise返回了,给到参数promiset
//前两次每次返回promise赋值给promiset形参后,都是执行return promiset.then() 进行判断, 输出 'ww'
//但最后一次,由于数组任务递归完毕,这一次不会再运行return promiset.then() 了,而是把第三个promise直接返回给了外界ress
//如果最后一次promise resolve了,则输出整个的then,如果没有resolve,就不会执行最终的then()代码
本文由 dealdot <dealdot#163.com> 创作, Full Stack Developer @ DeepBlue
本文最后编辑时间为: May 1, 2021 at 10:44 am
转载请注明来源