Не удается внедрить маршрутизатор в HttpInterceptor (Angular 7)

Я хочу внедрить Angular Router в свой HttpInterceptor. К сожалению, в консоли браузера выдается следующая ошибка:

TypeError: this.router не определен

Я, как обычно, добавил это в свой конструктор:

constructor (private router: Router) {

}

Кроме того, я сделал следующее в своем массиве поставщиков внутри app.module.ts:

{
  provide: HTTP_INTERCEPTORS,
  useClass: MyService,
  multi: true,
  deps: [Router]
}

Я хочу использовать текущий URL-адрес внутри оператора if в моем обработчике ошибок, чтобы предоставить определенные функции для разных маршрутов:

myErrorHandler(error: HttpErrorResponse) {
   if (this.router.url === 'test') {
     // do something
   } else {
     return throwError(error).pipe(
       // do something
     );
   }
}

Что я делаю неправильно?


comment
Не могли бы вы дать еще контекст? код в вопросе выглядит нормально.   -  person Lemon    schedule 30.04.2019
comment
@Lemon Я обновил свой вопрос. Я хочу получить текущий маршрут (URL-адрес) в моем перехватчике и использовать его в обработчике ошибок.   -  person Codehan25    schedule 30.04.2019
comment
@ Codehan25 Удалось ли вам решить эту проблему? Я столкнулся с той же проблемой с той же настройкой.   -  person Babyburger    schedule 04.04.2020


Ответы (3)


Я нашел ответ в другой соответствующей теме: Angular 6 Service не определен после введения в перехватчик

По сути, внедренная переменная конструктора недоступна из функции, которую вы передаете функции catchError. Вам нужно получить доступ к router прямо в вашем «методе перехвата» следующим образом:

constructor(private router: Router) {
}

intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    return next.handle(request).pipe(
        catchError((errorResponse: HttpErrorResponse) => {
            // this.router is defined here
        })
    );
}

Проблема, кажется, кроется в catchError. Если вы распечатаете текущую область this в функциях intercept и catchError, вы получите MyInterceptor и CatchSubscriber соответственно. this.router недоступен у CatchSubscriber. Вы по-прежнему можете использовать отдельные функции, добавив частный метод в свой класс перехватчика:

intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    return next.handle(request).pipe(
        catchError((errorResponse: HttpErrorResponse) => {
            this.handleError(errorResponse);
        })
    );
}

private handleError(errorResponse: HttpErrorResponse) {
     // this.router is defined here
}

Обобщить:

catchError(this.handleError)  // does not work because of different scope

catchError(err => this.handleError(err))  // works because of same scope
person Babyburger    schedule 04.04.2020
comment
это избавило меня от головной боли. - person vadimbog; 04.06.2020

Вы это сделали? Слишком очевидно?

import { Router } from "@angular/router";
person Robin Webb    schedule 30.04.2019
comment
Конечно :) Я думаю, что в Interceptors есть что-то особенное, но я ничего не могу найти в документации. - person Codehan25; 30.04.2019

Вы можете попробовать использовать инжектор.

constructor(inj: Injector) {
this.router = inj.get(AuthService) }

Следует отметить, что невозможно импортировать службу, содержащую httpClientModule, чтобы избежать циклической зависимости.

person Seinei    schedule 30.04.2019