catchError之后的switchMap不会发出值

时间:2019-05-29 17:45:20

标签: angular rxjs reactive-programming

我正在使用Angular和RxJS。

我打算将一个项目添加到集合(第一个可观察的对象),然后获取该集合(第2个可观察的对象),所有内容都在同一数据流上。

然后我将Observable提供给组件,然后子组件通过异步管道接收它。

第一个addItem AJAX调用失败时,将出现问题。我试图继续返回收集项目的整个更新列表,因此子组件具有新数据,但是最后一步从未完成,并且在addItem失败后子项目也永远不会收到该集合。

这是我的代码:

public addItem(item) {

  this.itemCollection$ = this.itemService.addItem(item).pipe(
        catchError((err) => {
          this.logger.error('Couldnt add Item to Collection');
          return of();
        }),
        switchMap(() => 
  this.itemsService.getItemsByItemId(this.itemId)));

}

控制台结果:

POST http://localhost:3000/api/XXXX/XXX/XXXXX/items 400 (Bad Request)
ngx-logger.js:245 2019-05-29T17:25:39.557Z ERROR [items-page-module.9c3988b4c0f0dbc7bc65.hot-update.js:319] Couldnt add Item to Collection

因此控制台上会记录错误,但是子组件永远不会获得新的项目列表。

我应该怎么做,尽管出现错误,itemCollection $ observable仍会发出项目的集合?

谢谢!

1 个答案:

答案 0 :(得分:4)

当您调用of()时,它会创建一个可观察的事件,该事件发出只是立即完成,因为它没有任何参数。问题在于switchMap()运算符只会在响应发出的值时触发。

因此,以下内容有效地沉默了所有可观察到的错误。

    throwError('ouch').pipe(
        catchError(() => of())
    ).subscribe(()=> {
         console.log('I am never printed');
    }, ()=> {
         console.log('I am never printed');
    }, ()=> {
         console.log('COMPLETED!'); // this will be printed.
    });

在上面的示例中,catchError()转换为可观察到的。订户回调或错误回调均不执行。仅执行完整的回调。

catchError()之后的任何运算符都不会被使用,因为不会发出任何东西。

您可以通过发出 undefined 或任何其他值来修复

public addItem(item) {
    this.itemCollection$ = this.itemService.addItem(item).pipe(
        catchError((err) => {
          this.logger.error('Couldnt add Item to Collection');
          return of(undefined);
        }),
        switchMap(() => this.itemsService.getItemsByItemId(this.itemId)));
}