NGXS - 处理分派多个动作

NGXS - Handling of dispatching multiple actions

简介:

我有一个 Angular 应用程序,它使用 NGXS 作为状态管理模式,Angular Material 用于 UI 组件(例如用于通知的 snackbars)。 该应用程序有几个不同的操作,我想在用户单击保存按钮时立即发送这些操作。之后,如果所有操作都已成功发送,我想通知用户。

问题:

即使一个操作失败,我仍然会收到消息 'Changes were successfully saved',但操作本身会记录发生的错误。有没有办法以不同的方式处理保存功能中的错误?

操作 1 - 上传头像

  @Action(UploadAvatar)
  public uploadAvatar(ctx: StateContext<AuthStateModel>, action: UploadAvatar) {
    return this.uploadService.uploadAvatar(ctx.getState().token, action.avatar).pipe(
      tap((result: any) => {
        console.log(result);
      }),
      catchError((error: HttpErrorResponse) => {
        console.error(error);
        return of(ctx.patchState({ responseStatus: error.status }));
      })
    );
  }

操作 1 - 更新用户

  @Action(UpdateUser)
  public updateUser(ctx: StateContext<AuthStateModel>, action: UpdateUser) {
    return this.userService.updateUser(ctx.getState().token, action.user).pipe(
      tap((result: any) => {
        console.log(result);
      }),
      catchError((error: HttpErrorResponse) => {
        console.error(error);
        return of(ctx.patchState({ responseStatus: error.status }));
      })
    );
  }

保存功能

  public save() {
    try {
      this.store.dispatch(new UploadAvatar(this.avatar));
      this.store.dispatch(new UpdateUser(this.user));
      this.snackbar.showSnackbar('Changes were successfully saved');
    } catch (error) {
      this.snackbar.showSnackbar('Changes could not be saved');
    }
  }

您正在使用 catchError 捕获 rxjs 中的错误,因此它永远不会到达您的 try/catch。调度也是异步的,因此它将始终显示 showSnackbar 和成功消息。这可能会更好。

未经测试的代码,但也许您会更好地理解这个想法

public save(): void {
  this.store.dispatch([
    new UploadAvatar(this.avatar),
    new UpdateUser(this.user)
  ]).subscribe({
    next: () => this.snackbar.showSnackbar('Changes were successfully saved'),
    error: () => this.snackbar.showSnackbar('Changes could not be saved')
  });
}
@Action(UploadAvatar)
public uploadAvatar(ctx: StateContext<AuthStateModel>, action: UploadAvatar) {
  return this.uploadService.uploadAvatar(ctx.getState().token, action.avatar).pipe(
    catchError((error: HttpErrorResponse) => {
      ctx.patchState({ responseStatus: error.status });

      return throwError(error);
    })
  );
}

@Action(UpdateUser)
public updateUser(ctx: StateContext<AuthStateModel>, action: UpdateUser) {
  return this.userService.updateUser(ctx.getState().token, action.user).pipe(
    catchError((error: HttpErrorResponse) => {
      ctx.patchState({ responseStatus: error.status });

      return throwError(error);
    })
  );
}

基本上,你在你的状态中捕获错误,将响应状态写入状态,并重新抛出相同的错误,可以通过调度捕获