【问题标题】:catchError in interceptor eliminates ability to cancel request拦截器中的 catchError 消除了取消请求的能力
【发布时间】:2019-01-30 14:56:11
【问题描述】:

我在某些组件中有请求,例如,通过点击:

performRequest() {
    const request = this.http
      .get('https://randomfox.ca/floof/')
      .subscribe();

      request.unsubscribe();
}

我有 http 拦截器:

@Injectable()
export class MyInterceptor implements HttpInterceptor {
    public intercept(req: HttpRequest<any>, next: HttpHandler) {
        return next.handle(req); // all is ok
        return next.handle(req).pipe(catchError(e => throwError(e))); // request can't be cancelled now
    }
}

如果第一个 return 正在工作 - 请求被 unsubscribe() 取消,但第二个 - 它没有被取消(我说的是请求级别的取消,比如请求没有挂起而是被取消)。

为什么会这样以及如何处理拦截器中的错误并具有取消请求的能力?

【问题讨论】:

  • 我看不出您的代码示例有什么问题。你能用stackblitz.com重现这个问题吗?
  • @cgTag stackblitz.com/edit/angular-z1uujx - 我在 stackblitz 上试过了,在这里它工作正常,所以可能直接在我的应用程序中的某个地方
  • 是的,我发现您的代码示例没有任何问题,并且没想到它会被复制。这将是 Angular 中的一个严重错误,会影响每个人。在源代码中搜索 share() 运算符或任何其他多播运算符。这些运营商干扰取消。如果你需要取消和使用share,那么在share之前添加一个takeUntil()。
  • @cgTag 我还有一个问题 - 可能你有一些想法。我稍微更新了 stackblitz - 我为请求添加了 10 毫秒的超时,并在拦截器中的 catchError cb 中添加了 console.log - 当出现超时错误时,拦截器的捕手不会被触发。请你告诉我为什么会这样
  • 应该被抓住。超时引发异常。

标签: angular


【解决方案1】:

我找到了一些解决方法,所以它可能会有所帮助 - return next.handle(req).pipe(tap(noop, (err: any) =&gt; /* handle somehow*/));

另外,我想提一下,我已经在单独的(和 +- 干净的)角度项目中尝试过,但问题没有重现

【讨论】:

  • 在 stackblitz 上它也可以正常工作 - 不能说为什么我现在在我的代码库中遇到它
  • stackblitz (stackblitz.com/edit/angular-z1uujx) 正在取消所有请求。即使是那些退订的人也会在代码中被注释掉。
猜你喜欢
  • 2014-04-01
  • 2018-10-31
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-03-08
  • 1970-01-01
  • 2020-01-05
相关资源
最近更新 更多