Hi I'm trying to understand why it gives me this infinite loop
i've tried lookin up the internet but nothing fits my need
this is my effect
/**
* EFFECT TO GET ALL USRS FROM THE KEYCLOAK SERVER
*/
loadUsers$ = createEffect(() => this.action$.pipe(
ofType(LOAD_USERS),
switchMap(() => {
return this.userService.fetchAll().pipe(
map((data: T[]) => LOAD_USERS_SUCCESS({ list: data }))
)
}), catchError((err) => {
return of(LOAD_USERS_FAILED({ error: err }))
})
))
/**
* FETCH GROUP PER USER
*/
loadUserGroup$ = createEffect(() => this.action$.pipe(
ofType(LOAD_USER_GROUP),
switchMap((action) => {
return this.userService.fetchGroupUser(action.id).pipe(
map((data: any[]) => LOAD_USER_GROUP_SUCCESS({ id: action.id, list: data }))
)
}), catchError((err) => {
return of(LOAD_USER_GROUP_FAILED({ error: err }))
})
))
and this is how i dispatch
sub-component.ts
ngOnInit(): void {
console.log(`user id ${this.userId}`)
this.store$.dispatch(LOAD_USER_GROUP({ id: this.userId }))
}
parent.ts
users$: Observable<User[]> = this.store$.select(selectAll)
isLoading$: Observable<boolean> = this.store$.select(isLoading)
isLoadingOther$: Observable<boolean> = this.store$.select(isLoadingOther)
constructor(private store$: Store<any>) {
this.store$.dispatch(LOAD_USERS())
}
reducer
export const userReducer = createReducer(
initialState,
/**
* ==============================================
* LOADING REDUCERS
* ==============================================
*/
on(LOAD_USERS_SUCCESS, (state, { list }) => {
return adapter.addAll(list, {
...state,
selectedUserId: undefined,
isLoading: false,
})
}),
on(LOAD_USERS_FAILED, (state, err) => {
return {
...state,
error: err,
selectedUserId: undefined,
isLoading: false,
}
}),
on(LOAD_USERS, (state) => {
return {
...state,
error: undefined,
selectedUserId: undefined,
isLoading: true
}
}),
/**
* ==============================================
* END OF LOADING REDUCERS
* ==============================================
*/
on(LOAD_USER_GROUP, (state) => {
return {
...state,
error: undefined,
selectedUserId: undefined,
isOtherLoading: true
}
}),
on(LOAD_USER_GROUP_SUCCESS, (state, { id, list }) => {
return adapter.updateOne({
id: id,
changes: { ...state.entities[id], group: list }
}, { ...state, isLoading: false, isOtherLoading: false, error: undefined })
}),
)
I made sure that the effect is not calling itself to cause the infinite loop. or calling another action that will ultimately call itself.
but still it is giving me infinite loop.
UPDATE I observe if i remove this part in the reducer it is not giving me the infinite loop result but I need it to update my selected entity.
on(LOAD_USER_GROUP_SUCCESS, (state, { id, list }) => {
return adapter.updateOne({
id: id,
changes: { ...state.entities[id], group: list }
}, { ...state, isLoading: false, isOtherLoading: false, error: undefined })
}),
UPDATED I updated the way i retrieve the user below. In just 1 compoenent
ngOnInit(): void {
this.sub.add(
this.store$.select(routerInfo).pipe(
concatMap(routerValue => {
const id = routerValue.params['id'];
return this.store$.select(selectUserById(id)).pipe(
tap(() => this.store$.dispatch(LOAD_USER_GROUP({ id: id }))),
map((user: User) => {
console.log(JSON.stringify(user))
})
)
})
).subscribe(() => {
this.isLoading$ = this.store$.select(isLoading)
})
)
}