手写 Promise - 串联 Promise

const MyPromise = (() => {
    const PENDING = "pending",
        RESOLVED = "resolved",
        REJECTED = "rejected",
        //不能让外部访问
        PromiseValue = Symbol("PromiseValue"),//状态数据
        PromiseStatus = Symbol("PromiseStatus"),//当前状态
        changeStatus = Symbol("changeStatus"),
        thenables = Symbol("thenables"),
        cachables = Symbol("cachables"),
        settleHandle = Symbol("settleHandle");
        linkPromise = Symbol("linkPromise");

    return class MyPromise {
        [changeStatus](newStatus, newValue, queue) {
            if (this[PromiseStatus] != PENDING) {
                //状态无法变更
                return;
            };
            this[PromiseStatus] = newStatus;
            this[PromiseValue] = newValue;
            //执行响应队列中的函数
            queue.forEach(handler => handler(newValue));
        };

        // executor 未决阶段(pending 状态)下的处理函数
        constructor(executor) {
            this[PromiseStatus] = PENDING;
            this[PromiseValue] = undefined;

            this[thenables] = [];//后续处理函数的数组 --> resolved
            this[cachables] = [];//后续处理函数的数组 --> rejected

            const resolve = data => {
                this[changeStatus](RESOLVED, data, this[thenables]);
            };

            const reject = reason => {
                this[changeStatus](REJECTED, reason, this[cachables]);
            };

            try {
                executor(resolve, reject);
            } catch (err) {
                reject(err);
            };
        };

        // handler 后续处理函数
        // immediatelyStatus 需要立即执行的状态
        // queue 作业队列 
        [settleHandle](handler, immediatelyStatus, queue) {
            if (typeof handler !== "function") return;

            if (this[PromiseStatus] == immediatelyStatus) {
                setTimeout(() => {
                    handler(this[PromiseValue])
                }, 0);
            } else {
                queue.push(handler);
            }
        }

        [linkPromise](thenable, catchable) {
            function exec(data, handler, resolve, reject) {
                try {
                    const result = handler(data);
                    if (result instanceof MyPromise) {
                        result.then(d => {
                            resolve(d);
                        }, err => {
                            reject(err);
                        });
                    } else {
                        resolve(result);
                    };
                } catch (err) {
                    reject(err);
                };
            };

            return new MyPromise((resolve, reject) => {
                this[settleHandle](data => {
                    exec(data, thenable, resolve, reject);
                }, RESOLVED, this[thenables]);

                this[settleHandle](reason => {
                    exec(reason, catchable, resolve, reject);
                }, RESOLVED, this[cachables]);
            });
        }
        
        then(thenable, catchable) {
            return this[linkPromise](thenable, catchable);
        }

        catch(cachable) {
            this[settleHandle](cachable, REJECTED, this[cachables]);
            return this[linkPromise](undefined, catchable);
        }
    };
})();

const pro = new MyPromise((resolve, reject) => {
    setTimeout(() => {
        resolve(1);
    }, 3000);
});

pro.then(data => {
    console.log(1, data);
    return 123;
}).then(data => {
    console.log(2, data);
    return new MyPromise(resolve => {
        resolve(456);
    });
}).then(data => {
    console.log(3, data);
    return 789;
});
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。