ngrx 8 effects dispatch action of other type
我在这里向您介绍有关ngrx效果的信息,我尝试做的是让一个函数登录名分配一个操作类型的登录名,对此操作产生的影响将使我的服务使用api进行调用。
在此返回令牌之后,我想调度其他两个操作,一种是getUserMenu类型,另一种是getUserInfo类型。这两个动作将具有不同的类型并具有不同的效果。
我最后有3家商店:
一个用于令牌和身份验证
一个用于用户信息
一个用于菜单信息
我尝试过这样的事情:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | login = createEffect( () => this.actions$ .pipe( ofType(authLogin), tap(action => { console.log("EFFECT LOGINNNN"); return this.authService.postLogin(action.username, action.password).pipe( map((data: any) => { console.log("AUTHTHHTHTH DATATA", data); let props = data.token; let payload = { token: data.token, isAuthenticated: true } this.store.dispatch(moMenuHttpGetListAction({US_ID: action.username})); this.store.dispatch(userHttpGetInfoAction({US_ID:action.username})); this.localStorageService.setItem(AUTH_KEY, payload); })) }) ), { dispatch: true } ); |
如果我设置了调度错误的登录工作,但是没有调用获取用户信息和用户菜单的方法
但是当我将dispatch设置为true时,我在相同的效果上有无限循环
动作moMenuHttpGetListAction
看起来像这样:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | moMenuHttpGetListEffect = createEffect( () => this.actions$.pipe( ofType(moMenuHttpGetListAction), switchMap(action => { console.log("MOMENU LOGINNNN"); return this.moMenuService.getKmApplications(action.US_ID).pipe( map((data: any) => { console.log("MOMENU DATATA", data); console.log("MOMENU DATATA", action.US_ID); let payload = { MO_MENU: data } this.store.dispatch(moMenuSetListAction({payload: data})); this.localStorageService.setItem(MENU_KEY, payload); })) }) ), { dispatch: false } ); |
但是在这一点上,当我将dispatch设置为true时,出现了错误编译。
我的动作看起来像:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | import { createAction } from"@ngrx/store"; import { props } from"@ngrx/store"; import { MoMenu, MoMenuState } from"./mo_menu.models"; //TODO CHANGER ME_ID en US_ID export const moMenuGetErrorAction = createAction("[User] Get Info"); export const moMenuGetIsLoadingAction = createAction("[User] Get Info"); export const moMenuSetErrorAction = createAction('[MoMenu] HTTP GET ACTION', props<{error: string}>() ); export const moMenuSetLoadingAction = createAction('[MoMenu] HTTP GET ACTION', props<{loading: boolean}>() ); export const moMenuHttpGetListAction = createAction('[MoMenu] HTTP GETLIST ACTION', props<{US_ID: string}>() ); export const moMenuHttpGetListErrorAction = createAction('[MoMenu] HTTP GET ACTION Error', props<{error: any}>() ); export const moMenuGetListAction = createAction("[MoMenu] Get List"); export const moMenuSetListAction = createAction("[MoMenu] Set Mo Menu List", props<{payload: MoMenu[]}>()); export const moMenuDeleteAction = createAction("[MoMenu] Delete List"); |
当有人要求我补充时,这些是两个减速器:
Ngrx对我来说有点新,所以我很乐意为此提供帮助=)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 | import { AuthState } from './auth.models'; import { authLogin, authLogout , authGetErrorAction, authGetIsLoadingAction, authSetErrorAction, authSetIsLoadingAction } from './auth.actions'; import { createReducer, on, Action } from '@ngrx/store'; export const initialState: AuthState = { isAuthenticated: false, token: undefined, isLoading: false, HttpResponse: undefined }; const reducer = createReducer( initialState, on(authSetErrorAction, (state, { error }) => ({ ...state, HttpResponse: error })), on(authSetIsLoadingAction, (state, { isLoading }) => ({ ...state, isLoading: isLoading })), on(authLogin, state => ({ ...state, isAuthenticated: true })), on(authLogout, state => ({ ...state, isAuthenticated: false })) ); export function authReducer( state: AuthState | undefined, action: Action ): AuthState { return reducer(state, action); } import { MoMenuState } from"./mo_menu.models"; import { moMenuGetListAction, moMenuDeleteAction, moMenuHttpGetListAction, moMenuSetListAction, moMenuHttpGetListErrorAction, moMenuGetErrorAction, moMenuGetIsLoadingAction, moMenuSetErrorAction, moMenuSetLoadingAction } from"./mo_menu.actions"; import { createReducer, on, Action } from"@ngrx/store"; export const initialState: MoMenuState = { isLoading: false, HttpResponse: undefined, MoMenuItems: null } const reducer = createReducer( initialState, on(moMenuSetErrorAction, (state, { error }) => ({ ...state, HttpResponse: error })), on(moMenuSetLoadingAction, (state, { loading }) => ({ ...state, isLoading: loading })), on(moMenuHttpGetListErrorAction, (state, { error }) => ( undefined)), on(moMenuSetListAction, (state, { payload }) => ({ ...state, MoMenus: payload })), on(moMenuHttpGetListAction, (state, { US_ID }) => ({ ...state })), on(moMenuGetListAction, state => state), on(moMenuDeleteAction, state => state) ); export function moMenuReducer( state: MoMenuState | undefined, action: Action ): MoMenuState { return reducer(state, action); } |
你们中的一些人对我有什么想法吗?
由于NgRx 8中的另一个动作,这就是我调度多个动作的方式:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 | @Injectable() export class MyEffects { myAction$ = createEffect(() => this.actions$.pipe( ofType(myActions.firstAction), switchMap(action => this.someService.getById(action.someId)), switchMap((sth: Something) => [ myActions.firstActionSuccess({ payload: sth }), myActions.secondAction({ payload: sth.xyz }), // ... more actions ]) ) ); constructor( private someService: SomeService, private actions$: Actions ) { } } |
动作如下所示:
1 2 3 | export const firstAction = createAction('First Action', props<{ someId: number }>()); export const firstActionSuccess = createAction('First Action Success', props<{ payload: Something }>()); export const secondAction = createAction('Second Action', props<{ payload: string }>()); |
希望有帮助!
您可以这样分配效果中的多个动作
1 2 3 4 5 6 7 8 9 10 11 | @Effect() someEffect$: Observable<Action> = this.actions$.pipe( ofType<SOME_ACTION>(SOME_ACTION), switchMap(_ => of( new myAction.Refresh(), new myAction.Clear() // another action ) ) ); |
还要确保有适当的效果,可以倾听您的操作以使其起作用