首页 > 解决方案 > Rxjs timeout() 运算符不在管道中工作

问题描述

嗨,我已经达到了以下代码的状态,除了超时之外,所有代码都在工作:

public monitorTask$(id: string): Observable<TaskResponse> {
    return timer(0, 4000).pipe(
        switchMap(() => this.fetchTaskStatus(taskId)),
        timeout(120000),
        takeWhile(res => this.isInProgress(res), true)
    );
}

private postTask(id: string) {
    this.monitorTask$(id).subscribe(
        state => {
            if (state.status === "SUCCESS") {
                this.onSuccess();
            }
            if (state.status === "FAILURE) {
                this.onFailure();
            }
        },
        (err) => {
            this.showError();
        }
    );
}

也试过这个:

public monitorTask$(id: string): Observable<TaskResponse> {
    return interval(4000).pipe(
        flatMap(() => this.fetchTaskStatus(id)),
        takeWhile(res => this.isInProgress(res.status), true),
        timeout(120000)
    );
}

我期望超时出错并在 postTask() 中输入 (err) 块,但它永远不会达到超时。我一直在玩不同的变体,但似乎没有把它弄好。这是我拥有的最干净的一个,所以如果有人看到我缺少的东西,我会非常感激!

标签: angularrxjstimeout

解决方案


这里有很多事情需要考虑。

  1. 发射间隔(timer4s)小于timeout(120s)。所以timeout永远不会触发,因为timer每 4 秒发射一次。
  2. 将 a 管道timeout连接到 RxJS 内置 observabletimer在逻辑上几乎没有意义。我相信你想通过管道timeout传递给this.fetchTaskStatus()函数。
  3. 在这种情况下,还有一个问题。这里使用的映射运算符是,当外部 observable ( ) 发出时switchMap,它将取消现有的内部 observable ( )。很可能您正在寻找运营商。但请注意,对于 的每次发射,都会单独触发。this.fetchTaskStatus()timerflatMaptimerthis.fetchTaskStatus()
public monitorTask$(id: string): Observable<TaskResponse> {
    return timer(0, 4000).pipe(
        flatMap(() => 
            this.fetchTaskStatus(id).pipe(
                timeout(120000)
            )
        ),
        takeWhile(res => this.isInProgress(res.status), true),
    );
}

推荐阅读