我的效果分配了无效的动作或无限循环

问题描述 投票:0回答:1

我是ngrx的新手,我希望有人能和kind可亲并帮助我,因为我阅读了很多有关此问题的主题,而我仍然持相同观点。我正在测试@ngrx/effects,我只想在应用程序启动时返回一个简单的用户角色数组(只是为了了解当前的工作方式)。当我在下面使用此代码时:

 ...
 ...
 switchMap(() => this.roleService.getAllRoles().pipe(
   map(roles => {
     return new AllRolesLoaded({ roles });
   }),
   catchError((error) => of(new ErrorLoadRole(error)))
 )),
// I got infinite loop

我有一个无限循环。通过对堆栈流的研究,我发现我必须使用.tap()而不是.map()。但是当我使用.tap()

 ...
 ...
 switchMap(() => this.roleService.getAllRoles().pipe(
   tap(roles => {
     return new AllRolesLoaded({ roles });
   }),
   catchError((error) => of(new ErrorLoadRole(error)))
 )),

// I got this:
// core.js:6014 ERROR Error: Effect "RoleEffects.loadRoles$" dispatched an invalid action:   ...
// core.js:6014 ERROR TypeError: Actions must have a type property

对于无效操作,我尝试:-Effect dispatched an invalid action:-具有装饰器@Effect(ngrx 8.0.1)的版本,版本createEffect()(ngrx 8.3.0)。-swithMap()mergeMap()exhaustMap()等...并且我得到了sama结果。

这里有完整的代码,也许您可​​以了解这里发生的事情。

//  #actions/role.actions.ts

// ngrx version 8.0.1
export enum RoleActionTypes {
  RequestLoadRoles = '[Role] Request Load data Roles',
  AllRolesLoaded = '[Roles API] All Roles Loaded',
  ErrorLoadRole = '[Roles API] Error load roles',
}

export class RequestLoadRoles implements Action {
  readonly type = RoleActionTypes.RequestLoadRoles;
}
export class AllRolesLoaded implements Action {
  readonly type = RoleActionTypes.AllRolesLoaded;
  constructor(public payload: { roles: Role[] }) {}
}
export class ErrorLoadRole {
  readonly type = RoleActionTypes.ErrorLoadRole;
  constructor(public payload: HttpErrorResponse) {}
}

// ngrx version 8.3.0 but i cannot handle it yet
// export const RequestLoadRoles = createAction('[Role] Request Load data Roles');
// export const AllRolesLoaded = createAction('[Roles API] All Roles Loaded', props<{ role: Role[] }>());

 export type RoleActions =
   | RequestLoadRoles
   | AllRolesLoaded
   | ErrorLoadRole
   ;

//  #effects/role.effect.ts

@Injectable()
export class RoleEffects {

// ngrx version 8.0.1
@Effect()
loadRoles$ = this.actions$.pipe(
  ofType<RequestLoadRoles>(RoleActionTypes.RequestLoadRoles),
  withLatestFrom(this.store.pipe(select(roles => roles.rolesLoaded))),
  filter(([action, loaded]) => !loaded),
  switchMap(() => this.roleService.getAllRoles().pipe(
    tap(roles => { // with .tap() i got the invalid dispatched action, i dont know why, and .map() give my an infinite loop
      return new AllRolesLoaded({ roles });
    }),
    catchError((error) => of(new ErrorLoadRole(error)))
  )),
);

// ngrx version 8.3.0 but i cannot handle it yet
// loadRoles$ = createEffect(() => this.actions$.pipe(
//   ofType('[Roles API] All Roles Loaded'),
//   mergeMap(() => this.roleService.getAllRoles()
//     .pipe(
//       map(roles => ({ type: '[Roles API] All Roles Loaded', payload: roles })),
//       catchError(() => EMPTY)
//     ))
//   )
// );

@Effect()
init$: Observable<RoleActions> = defer(() => {
  return of(new RequestLoadRoles());
});
constructor(private actions$: Actions, private store: Store<RolesStateEntity>, private roleService: RoleService) {}

}

这里是控制台的全部错误:

core.js:6014 ERROR Error: Effect "RoleEffects.loadRoles$" dispatched an invalid action: [{"name":"ADMIN","permissions":["fullAccessUserManagement","canDeleteUserManagement","canUpdateUserManagement","canReadUserManagement"]},{"name":"MODERATOR","permissions":["canDeleteUserManagement","canUpdateUserManagement","canReadUserManagement"]},{"name":"USER","permissions":["canReadUserManagement"]},{"name":"GUEST","permissions":[]}]
at reportInvalidActions (effects.js:338)
at MapSubscriber.project (effects.js:428)
at MapSubscriber._next (map.js:29)
at MapSubscriber.next (Subscriber.js:49)
at ExhaustMapSubscriber.notifyNext (exhaustMap.js:60)
at InnerSubscriber._next (InnerSubscriber.js:11)
at InnerSubscriber.next (Subscriber.js:49)
at MergeMapSubscriber.notifyNext (mergeMap.js:69)
at InnerSubscriber._next (InnerSubscriber.js:11)
at InnerSubscriber.next (Subscriber.js:49)
...
Show 139 more frames
core.js:6014 ERROR TypeError: Actions must have a type property
at ActionsSubject.next (store.js:168)
at Store.next (store.js:709)
at SafeSubscriber.__tryOrUnsub (Subscriber.js:183)
at SafeSubscriber.next (Subscriber.js:122)
at Subscriber._next (Subscriber.js:72)
at Subscriber.next (Subscriber.js:49)
at MergeMapSubscriber.notifyNext (mergeMap.js:69)
at InnerSubscriber._next (InnerSubscriber.js:11)
at InnerSubscriber.next (Subscriber.js:49)
at Notification.observe (Notification.js:20)

[我在这里再次说,我得到了数据,但是我也得到了这个错误(当我使用.tap()时)。另一个错误是无限循环(.map())。

如果您能抽出宝贵的时间阅读我的话,我先谢谢您,感谢您的帮助,因为此时此刻我正处于黑洞中。

angular typescript ngrx roles ngrx-effects
1个回答
0
投票

您应该使用map而不是taptap不返回值,因此这意味着您将把服务的结果分派回导致无效操作错误的商店。使用map,您可以将服务响应转换为有效的NgRx操作。

您正在显示的代码是有效的,所以我想可能是其他原因导致了无限循环。

 switchMap(() => this.roleService.getAllRoles().pipe(
   map(roles => {
     return new AllRolesLoaded({ roles });
   }),
   catchError((error) => of(new ErrorLoadRole(error)))
 )),
© www.soinside.com 2019 - 2024. All rights reserved.