You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

TypeScript如何优雅等待仅回调无Promise返回的外部服务完成

解决方案

核心思路是将回调风格的第三方服务封装为Promise版本,再通过Promise.all等待所有并行调用执行完成后再判断结果,完全不需要定时器轮询。
之前直接给getInfoFromService添加async关键字不生效的原因是,async/await仅能等待Promise对象的状态变更,原生回调式方法没有返回Promise,无法被await感知到执行进度。

具体修改步骤

  • 第一步:封装回调式服务为Promise方法
    对原有的fakeService做一层包装,把回调触发的结果通过Promise的resolve抛出,这样就可以用await等待执行完成。
  • 第二步:改造getInfoFromService为异步方法
    收集所有并行调用的Promise实例,用Promise.all等待全部执行完成后,再返回校验结果。
  • 第三步:修改update方法适配异步逻辑
    等待getInfoFromService的异步返回结果后,再执行resolve/reject逻辑。

完整可运行代码

class Foo {
    
    a: number = 0;

    constructor () { }

    public fakeService(data: number, callback: (sugestion:number, query:number) => void): void {
        // 模拟耗时的外部服务
        var b = 42;
        var a = 12;

        setTimeout(() => {
            return callback(data * a + b, 0);
        }, 500)
    }

    // 新增:封装fakeService为返回Promise的方法
    private fakeServicePromise(data: number): Promise<[sugestion: number, query: number]> {
        return new Promise((resolve) => {
            this.fakeService(data, (sugestion, query) => {
                resolve([sugestion, query]);
            })
        })
    }

    public async update() {
        // 调用多个服务获取数据
        return new Promise(async (resolve, reject) => {
            // 等待异步方法返回结果
            let valid: boolean = await this.getInfoFromService();
            if (valid) {
                resolve("OK " + this.a);
            } else {
                reject("NOK " + this.a);
            }
        })
    }

    private async getInfoFromService(): Promise<boolean> {
        // 收集所有并行调用的Promise
        const servicePromises: Promise<void>[] = [];
        for (let i=0; i<5; i++){
            const p = this.fakeServicePromise(i).then(([sugestion]) => {
                this.a = Math.max(sugestion, this.a);
            })
            servicePromises.push(p);
        }
        // 等待所有服务调用全部执行完成
        await Promise.all(servicePromises);
        // 此时this.a已经更新为最终值,再做判断
        return this.a == 90;
    }
}

const foo = new Foo();

// update方法需要返回Promise用于触发后续更新
foo.update()
    .then(res => {
        console.log(res);
    })
    .catch(e => {
        console.log(e);
    });

运行结果说明

循环调用5次fakeService,i的取值是0~4,计算得到的sugestion最大值是4*12+42=90,所以最终会输出OK 90。

内容的提问来源于stack exchange,提问作者Nicolas M.

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.26 19:24:05