簡體   English   中英

帶有 rxjs 重播主題的 Http 錯誤處理程序攔截器配置 - Angular

[英]Http Error Handler Interceptor configuration w/ rxjs Replay Subject - Angular

我在嘗試獲取錯誤值並通過 html 元素顯示自定義錯誤消息時遇到問題。 我正在使用重播主題來存儲錯誤並管理我的攔截器中的錯誤狀態。 我正在將攔截器正確導入到組件中並在我的模塊中正確提供它。 我很困惑為什么從我的 API 獲得錯誤響應時我的錯誤沒有出現。

這是我到目前為止所擁有的

errorHandlerInterceptor.service.ts

export class ErrorHandlerInterceptor implements HttpInterceptor {

  error: ReplaySubject<string> = new ReplaySubject<string>(1);

  intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    return next.handle(request)
      .pipe(
        retry(1),
        catchError((error: HttpErrorResponse) => {
          let errorMessage = '';
          if (error.error instanceof ErrorEvent) {
            // client-side error
            errorMessage = `Error: ${error.error.message}`;
          } else {
            // server-side error
            errorMessage = `Error Code: ${error.status}`;
          }
          //window.alert(errorMessage);

          this.error.next(errorMessage);

          return throwError(this.error);
        })
      )
  }
}

然后在 html 中,如果 Replay Subject 有值,我異步管道重播主題只顯示錯誤消息。

組件.html

<div
    *ngIf="errorHandlerInterceptor.error | async"
    class="app-alert--error"
  >
    <p class="app-alert__title">
      ERROR
    </p>
    <p id="error-message">
      {{ errorHandlerInterceptor.error | async }}
    </p>
</div>

非常感謝任何幫助或建議!

在我看來,在組件內導入攔截器並不是一個好的模式。

解決此問題的一種方法可能是使用將錯誤傳播給其使用者的服務 這樣,在我看來,我們可以實現更好的關注點分離

錯誤.service.ts

@Injectable({
    providedIn: 'root'
})
export class ErrorService {
    private errorStore = new BehaviorSubject(null);
    public error$ = this.errorStore.asObservable();

    emitError (err) {
        this.errorStore.next(err);
    }
}

foo.component.ts

@Component{/* ... */}
export class FooComponent {

    get currentError$ () {
        return this.errorService.error$;
    }

    constructor (private errorService: ErrorService) { }
}

foo.component.html

<!-- ... -->

<div *ngIf="currentError$ | async">
    Error!
</div>

<!-- ... -->

error.interceptor.ts

constructor (private errorService: ErrorService) { }

intercept (/* ... */) {
    return next.handle(req)
        .pipe(
            /* ... */
            catchError(err => {
                /* ... */

                // If error found
                this.errorService.emitError(errorMessage);

                /* ... */
            }),
        )
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM