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

AngularJS Promise链式调用中service的catch执行后controller的then仍触发?

问题根因分析

核心是service.ts里的someMethod存在两处逻辑错误,导致最终返回给controller的promise状态是已解决(resolved):

  • 错误1:返回了错误的Promise对象
    你在someMethod内部手动创建了deferred对象,但最终没有返回deferred.promise,而是直接返回了OtherService.otherMethod()的链式调用结果。你在catch里执行的deferred.reject(reason)完全没有作用,因为这个deferred对象的promise从来没有被返回给调用方。
  • 错误2:catch回调没有返回rejected状态的Promise
    Promise的catch回调如果没有主动抛出错误、或者返回一个rejected状态的Promise,那么catch执行完成后会默认返回一个resolved状态的Promise,链式调用就会走到后续的then分支。你当前someMethod里的catch只执行了无意义的deferred.reject(reason),没有做任何中断resolve的操作,所以最终返回给controller的Promise是resolved状态,自然会走到then块。
修复方案

两种修复方式二选一即可:

方案1:删除冗余deferred,直接在catch里返回rejected状态

someMethod(): ng.IPromise<void> {
    return this.OtherService.otherMethod()
    .catch ( e => {
        // 主动抛出错误,让链式调用返回rejected状态
        throw e;
        // 也可选择用$q返回rejected:return this.$q.reject(e);
    });
}

方案2:保留deferred写法,返回正确的promise对象

someMethod(): ng.IPromise<void> {
    const deferred = this.$q.defer<void>();
    this.OtherService.otherMethod()
    .then(() => deferred.resolve())
    .catch ( e => {
        deferred.reject(e);
    });
    // 此处必须返回手动创建的deferred对应的promise
    return deferred.promise;
}

内容的提问来源于stack exchange,提问作者Luciano Borges

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.05 05:06:04