在使用 NGRX 使用 observables 调用 API 之前检查 Angular Store 中的数据

Posted

技术标签:

【中文标题】在使用 NGRX 使用 observables 调用 API 之前检查 Angular Store 中的数据【英文标题】:Check data in Angular Store before calling API with NGRX using observables 【发布时间】:2018-11-15 06:36:49 【问题描述】:

我正在使用带有 NGRX 效果的 Angular,而且我是 observables 世界的新手。我想检查我的商店中是否存在数据,那么不应该调用 API,并且应该从商店中提取数据。我设法发现我可以使用 withLatestFrom() 来检查商店中的最新值。下一部分让我感到困惑,我无法让它工作。我当前的代码如下:

 @Effect() getSomeContent$ = this.actions$
    .ofType(GET_SOME_CONTENT)
    .withLatestFrom(this.store$.select('store-section'))
    .map(([action, store]) => 
        const content = ;
        if (store.someContent.length > 0) 
           return new GetCategoryContentSuccessAction( categoryContent: categories );
        
        return Observable.from(action.payload);
    )
    .switchMap(payload => this.APIcall(payload)
        .then(data => 
            const content = ;
            data.items.map((item) => 
                const slug = data.slug;
                content[slug] = 
                    info: datasomeData
                ;
            );
            return new GetSomeContentSuccessAction( categoryContent: categories );
        )
        .catch((err) => 
            return new GetFailureAction( error:  );
        )
    );

我想使用某种 if 或 else 语句来检查商店。如果数据存在,我想为我必须处理的减速器发回一个空对象。如果不是,我想调用 API 并将该数据发回。我不知道 observable 是否可以换句话说可以分支所以可以做到这一点?

有没有更好的方法可以实现这一目标?可能通过创建另一个操作来单独处理 API。我想了解未来的最佳实践。任何帮助将不胜感激。

【问题讨论】:

【参考方案1】:

我正在研究解决这个确切问题的方法,所以我想我会把我的 2 美分放在这里,以防其他人发现它有帮助。

有一篇很棒的文章Stop Using NGRX Effects For That。其中谈到了尝试将其塞入ngrx效果链中是多么复杂。

相反,他们建议使用我一直在使用和喜爱的服务。一个简单的版本可能如下所示。

Service: 

public posts$ = this.store.select(postSelectors.selectAll)
    .pipe(
        tap(posts => 
            if (!posts.length) 
                this.store.dispatch(new postActions.LoadMany());
            
        ),
        filter(posts => posts !== null)
    );

在这里,我们基本上只是尝试选择我们想要的状态,如果它不存在,则调度一个动作,该动作将触发一个效果,从 api 获取它并将其推送到 store。

Component: 

this.posts$ = this.postService.posts$;

然后在您的组件中,您可以从您的服务中订阅 observable,而不关心它是否在商店中。然后,您可以在组件中订阅该值以获取值,也可以使用异步管道将其推送到模板。

这对于简单的东西非常有效,但是当您必须首先获取依赖于其他数据的数据时,我仍在研究更复杂的 RXJS 链。但是,这只是我编写 RXJS 函数的能力的限制。

【讨论】:

以上是关于在使用 NGRX 使用 observables 调用 API 之前检查 Angular Store 中的数据的主要内容,如果未能解决你的问题,请参考以下文章

如何从 RxJS combineLatest 中删除瞬态事件与 NGRX 存储源 observable

NGRX - 使用 jasmine-marbles 将 Promise 转换为 observables 的测试效果问题

Ngrx 相对于 Observable Data Services 架构的优势? [关闭]

ngrx effect 多次调用observer,但只调度了一个action

如何从 ngrx 存储中获取数据并将其更新到 Observable 变量中?

更新 ngrx/store 中的对象