【问题标题】:Get the full http response in case of an error发生错误时获取完整的 http 响应
【发布时间】:2019-01-24 09:29:19
【问题描述】:

在 Angular 文档中,他们声明您必须在提供的选项上指定 observe: "response" 才能获得完整的 http 响应,我在这里做了:

constructor(private service: new () => T,
  private http: HttpClient,
  private httpErrorHandler: HttpErrorHandlerService,
){ 
    this._handleError = this.httpErrorHandler.createHandleError(this.service.name);
}
private _handleError: HandleError;
//...other code
delete(resourceNameOrId: number | string): Observable<HttpErrorResponse>{
    return this.http.delete<T>(this._url + resourceNameOrId, {
      observe: "response"
    }).pipe(
      catchError(this._handleError(`delete`, null))
    );
  }

handleError 函数是在这个服务中定义的:

export type HandleError = <T> (operation?: string, result?: T) => (error: HttpErrorResponse) => Observable<T>;

@Injectable({
  providedIn: 'root'
})
export class HttpErrorHandlerService {

  constructor(private errorService: ErrorService, private modalService: NzModalService) { }

  createHandleError = (serviceName = '') => <T> (operation = 'operation', result = {} as T) => this.handleError(serviceName, operation, result);

  handleError<T> (serviceName = '', operation = 'operation', result = {} as T ){
    return (error: HttpErrorResponse): Observable<T> => {
      const message = (error.error instanceof ErrorEvent) ? error.error.message: `{error code: ${error.status}, body: "${error.message}"}`;
      this.errorService.errorMessage = `${serviceName} -> ${operation} failed.\n Message: ${message}`;
      console.error(this.errorService.errorMessage);
      return of(result);
    }
  }
}

这是我如何在组件中调用服务删除函数的示例:

this.service.delete(nom).subscribe(data => {
  if(!this.errorService.errorMessage){
    this.notificationService.success("Suppression", "L'enregistrement a été supprimée !");
  }
});

但在我的情况下指定 observe: "response" 不起作用,error: HttpErrorResponse 只返回错误消息而不是完整响应:

我在这个帖子中尝试了解决方案:Angular 4.3.3 HttpClient : How get value from the header of a response? 这对我不起作用,提供的解决方案是定义观察选项。

我该如何解决这个问题?

更新:

仅当删除http请求返回200代码时,观察选项才有效,如下图所示,但是当有404响应状态时,这种情况下的响应对象为空,并且在handleError函数中响应正文为我唯一可以访问的东西。

【问题讨论】:

  • 我试图在堆栈闪电战中复制您的问题,但我得到了作为 HttpErrorResponse 的完整错误响应,因为它应该是:stackblitz.com/edit/angular-hh4x4z 我不太确定您的问题是什么。请您自己提供一个堆栈闪电战,展示您的错误和您遇到的问题!

标签: angular error-handling rxjs


【解决方案1】:

通过 Interceptor 拦截 HttpClient 钩子适合你吗? 尝试这样的事情: 创建一个拦截器:

@Injectable()
export class FinalInterceptor implements HttpInterceptor {

constructor(private errorHandlerService: HttpErrorHandlerService) {}

  intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
      return next.handle(req).pipe(
        tap((event: HttpEvent<any>) => {
            if (event instanceof  HttpErrorResponse) {
              this.errorHandlerService.handleError(event);
            }
        }));
  }
}

应用模块:

providers: [
    ...
    { provide: HTTP_INTERCEPTORS, useClass: FinalInterceptor, multi: true },
  ],

所以在我的处理程序服务中,我遇到了 http 错误 next console.log.

我想这正是你要找的

【讨论】:

  • 谢谢,实际上问题是在应用程序中有人创建了一个拦截器来捕获错误并且只发送消息 xD!
  • 哈哈 x) 至少有用
【解决方案2】:

如果你想在你的 catchError 中包含 HttpErrorResponse 对象,请在 api 调用完成后尝试将它放入块中,如下所示:

delete(resourceNameOrId: number | string): Observable<HttpErrorResponse>{
    return this.http.delete<T>(this._url + resourceNameOrId)
 .pipe(
      catchError((error:any)=>{
           console.log(error);//error is the HttpErrorResponse object returned
           return this._handleError(`delete`, null)
      })
    );
  }

【讨论】:

  • 其实这段代码会产生如下错误:[ts] Argument of type '(error: any) =&gt; void' is not assignable to parameter of type '(err: any, caught: Observable&lt;HttpResponse&lt;T&gt;&gt;) =&gt; ObservableInput&lt;{}&gt;'. Type 'void' is not assignable to type 'ObservableInput&lt;{}&gt;'.
  • 你可以尝试在你的 handleError 方法中返回一个 ErrorObservable 吗? return ErrorObservable.create(result);
  • 你的意思是return throwError(result) 吗?因为在 Angular 6 中没有 ErrorObservable
  • 是的。试试看。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-11-10
  • 2017-07-23
  • 2020-07-24
  • 2018-12-30
相关资源
最近更新 更多