Для меня странно, что вы используете take(1)
. take(1)
принимает первое излучение и закрывает наблюдаемый поток (делая его мертвым). Я вижу, вы видите, существует ли то, что вы ищете, в магазине или нет, прежде чем сделать вызов API, сделав ваш магазин кэшем.
Я бы сделал:
@Effect()
myObjectivesRequested$ = this.actions$.pipe(
ofType<MyObjectivesRequested>(ObjectiveActionTypes.MyObjectivesRequested),
switchMap(({ payload }) => {
return this.store.pipe(
select(selectMyObjectivesIdsByCompanyId(payload.companyId)),
switchMap(myObjectives => {
if (myObjectives) {
return of(myObjectives);
} else {
return this.ObjectivesService.getMyObjectives(payload.companyId);
}
}),
map(objectives => new MyObjectivesLoaded({objectives, companyId: payload.companyId}))
),
// catch the error, return the action (this is optional)
catchError(error => Observable.of(new MyObjectivesError(error))
})
)
Некоторые примечания :
1.) select(selectMyObjectivesIdsByCompanyId(payload.companyId))
должна быть переменной в файле селекторов.
2.) Я вижу ваши диспетчерские действия с использованием магазина в вашем эффекте. В вашем редукторе прослушайте MyObjectivesRequested
и включите loading
. Прослушайте MyObjectivesLoaded
, заполните фрагмент данных / целей и выключите loading
. Прослушайте MyObjectivesError
и выключите loading
, а error
- любую ошибку. Затем вы должны иметь селекторы, как вы, для selectMyObjectivesIdsByCompanyId
(это срез данных / целей) для loading
и error
, а также использовать эти селекторы в вашем компоненте, чтобы увидеть, что происходит в состоянии.
Хороший репозиторий, связанный с ngrx
=> https://github.com/DeborahK/Angular-NgRx-GettingStarted, где Demo5 является наиболее продвинутым (из всех встроенных концепций).