Angular 可观察到的错误不会刷新界面 ChangeDetectionStrategy.OnPush

Angular observable on error does not refresh interface with ChangeDetectionStrategy.OnPush

我有一个使用服务提交一些数据的组件。

此组件使用 ChangeDetectionStrategy.OnPush,但发生了一些奇怪的事情:

据我了解,界面不应刷新,因为我使用 ChangeDetectionStrategy.OnPush 并且我正在更改基本类型字符串变量。

那么,¿为什么在 next 中触发变化检测?

组件

当服务发生错误时,我想在错误回调中接收它。

submit() {
    this.formStatus = 'sending';
    this._service.create(data).subscribe({
      next: () => {
        this.formStatus = 'success';
        // interface refreshes
      },
      error: () => {
        this.formStatus = 'error';
        // interface does not refresh
        console.log(this.formStatus); // prints 'error'
      },
    });
  }
<div *ngIf="formStatus === 'success'">
  ...
</div>

服务

调用 API 并使用 errorUtil.handle 捕获错误,这会引发 rxjs 错误(因为我想 return Observable.error)。

  create(requestData: Data): Observable<Data> {
    return this._http
      .post<HttpResponse<CreateResponse>>(
        MY_API.createUrl,
        JSON.stringify(requestData)
      )
      .pipe(
        catchError(this._errorUtil.handle()),
        map(data => this.onSuccessCreate(requestData, data))
      );
  }

错误处理程序

handle<T>(): (error: HttpErrorResponse, caught?: Observable<T>) => Observable<T> {
    return (error: HttpErrorResponse, caught?: Observable<T>) => {
      return throwError();
    };
  }

我试过将 return throwError(); 更改为 throw throwError(); 但行为是一样的。

这是一个奇怪的行为,我仍然不明白为什么在调用 next 时,界面会更新。应该也不更新了。

正确的方法是使用 stream 来监听表单状态的变化。

组件


type FormStatus = 'clean' | 'sending' | 'success' | 'error';
// ...
private _formStatus$: BehaviorSubject<FormStatus> = new BehaviorSubject<FormStatus>('clean');


set formStatus(status: FormStatus) {
    this._formStatus$.next(status);
}

get formStatus$(): Observable<FormStatus> {
    return this._formStatus$.pipe(
        shareReplay({ refCount: true, bufferSize: 1 })
    );
}
<div *ngIf="(formStatus$ | async) !== 'error'">
  ...
</div>