简体   繁体   English

来自 Observable 输出的 RxJS Observable 结果

[英]RxJS Observable result from an Observable's output

I have an Angular 8 application, that uses two layers to store data: StorageService abstracts away the actual HTTP service calls, while it itself does not contain other methods than get and save of various data types.我有一个 Angular 8 应用程序,它使用两层来存储数据: StorageService抽象出实际的 HTTP 服务调用,而它本身不包含除getsave各种数据类型之外的其他方法。

Other services like BookmarkService use StorageService and implement the more complex business logic like adding a new bookmarked article. BookmarkService等其他服务使用StorageService并实现更复杂的业务逻辑,例如添加新的书签文章。

The catch is, we might have to call StorageService twice, to load the data and then to save it.问题是,我们可能必须调用StorageService两次,以加载数据然后保存它。

I would like to expose potential errors to the caller site properly and I am wondering what the best solution would be to implement something like this, without introducing RxJS Subject objects at all.我想正确地向调用者站点公开潜在的错误,我想知道实现这样的事情的最佳解决方案是什么,根本不引入 RxJS Subject 对象。 For example, is there any way to achieve this via merely piping?例如,有没有办法仅通过管道来实现这一目标? Can someone please give me an example on how to properly implement this pattern?有人可以给我一个关于如何正确实现这种模式的例子吗?

export class BookmarkService {

  constructor(private storageService: StorageService) {}

  addArticleToBookmarks(article: Article): Observable<SaveResponse> {

    this.storageService.getBookmarkedArticles().subscribe(articles =>

      articles.push(article);

      this.storageService.saveBookmarkedArticles(articles).subscribe(saveResponse => ...)

    });

    // want to return an Observable of saveResponse, if getBookmarkedArticles completed, 
    // or the error output of getBookmarkedArticles if it failed
    return ...

  }

Do you mean something like this ?你的意思是这样的吗?

addArticleToBookmarks(article: Article): Observable<SaveResponse> {

  this.storageService.getBookmarkedArticles()
  .pipe(
    catchError(err => console.error(err))
    switchMap(articles => {
      articles.push(article);
      return this.storageService.saveBookmarkedArticles(articles);
    }
  ).subscribe(saveResponse => ...)

}

You can use a switchMap ormergeMap (also known as flatMap ) operator.您可以使用switchMapmergeMap (也称为flatMap )运算符。

Here's a good explanation about the difference between both: https://javascript.tutorialhorizon.com/2017/03/29/switchmap-vs-flatmap-rxjs/这是关于两者之间差异的一个很好的解释: https : //javascript.tutorialhorizo​​n.com/2017/03/29/switchmap-vs-flatmap-rxjs/

Example using switchMap :使用switchMap示例:

    addArticleToBookmarks(article: Article): Observable<SaveResponse> {
        return this.storageService.getBookmarkedArticles().pipe(
            switchMap(articles => {
                articles.push(article);
                return this.storageService.saveBookmarkedArticles(articles)
            })
        );
    }

I have not tested it, but I'm quite sure, this will work我还没有测试过,但我很确定,这会奏效

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM