我的Angular 5应用程序基于NgRx,一个类似于Redux但基于RxJS的状态管理库。
我经常需要根据当前操作的有效负载从商店获取最新值。
在RxJS术语中,这意味着我的主流不断生成项目,而每个新项目我需要根据项目的值创建一个侧流,从此流中获取最新值,以及将它与主流相结合。
目前,我这样做:
@Effect()
public moveCursor$: Observable<Action> = this.actions$.pipe(
ofType<TableAction.MoveCursor>(TableActionType.MOVE_CURSOR),
switchMap(action => this.store$.select(selectTableById(action.payload.cursor.tableId)).pipe(
first(),
map(table => ({action, table}))
)),
map(({action, table}) => {
...
})
)
我知道这可能不是最好的解决方案而且我正在寻找类似的东西(withLatestFrom
运营商无法做到这一点):
@Effect()
public moveCursor$: Observable<Action> = this.actions$.pipe(
ofType<TableAction.MoveCursor>(TableActionType.MOVE_CURSOR),
withLatestFrom(action => this.store$.select(selectTableById(action.payload.cursor.tableId))),
map(([action, table]) => {
...
})
)
所以我的问题是:是否有任何类似于withLatestFrom
的RxJS运算符可以将第一个流产生的值作为参数?
答案 0 :(得分:3)
您可以使用mergeMap
和map
将操作与从商店中选择的表格结合使用:
@Effect()
public moveCursor$: Observable<Action> = this.actions$.pipe(
ofType<TableAction.MoveCursor>(TableActionType.MOVE_CURSOR),
mergeMap(action => this.store$
.select(selectTableById(action.payload.cursor.tableId))
.pipe(
first(),
map(table => [action, table])
)
),
map(([action, table]) => {
...
})
)
您需要使用first
- 或take(1)
- 以确保从商店中选择的内部可观察量只发出一个值 - 表格是结合行动。
答案 1 :(得分:1)
我终于做到了...
doEffect$ = this.actions$.pipe(
ofType<someAction>(losActionTypes.someAction),
switchMap/mergeMap/concatMap( // according to your logic
action => of(action).pipe(
withLatestFrom(this.store.pipe(select(leFancySelector)))
)),
tap(console.log) // tap if you don't believe me
答案 2 :(得分:0)
不,从 rxjs 6 开始,我不相信有这样的内置运算符。我认为您当前的解决方案是最直接的方法,我也在使用该模式,重要的是要记住包含 first()
或 take(1)
以避免响应选择器。