4
votes

I wrote an HttpInterceptor (Angular 4.3.6) to catch all requests and manipulate some header fields. My problem is that it is not catching every request. What could be the problem?

Here my interceptor:

import {Injectable} from '@angular/core';
import {HttpEvent, HttpInterceptor, HttpHandler, HttpRequest, HTTP_INTERCEPTORS} from '@angular/common/http';
import {Observable} from 'rxjs/Observable';

@Injectable()
export class AuthInterceptor implements HttpInterceptor {


    intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {

        console.log('AuthInterceptor at work: ', req.url );

        const contentTypeReq = req.clone({
            headers: req.headers.set('Content-Type', 'application/json')
        });

        const token  = localStorage.getItem('token');
        if (token) {
            const authReq = contentTypeReq.clone({
                headers: req.headers.set('Authorization', 'Bearer ' + token)
            });
            return next.handle(authReq);
        }

        //debug - lazy loading
        //contentTypeReq.headers.keys()

        return next.handle(contentTypeReq);
    }
}


export const AuthInterceptorProvider = {
    provide: HTTP_INTERCEPTORS,
    useClass: AuthInterceptor,
    multi: true,
};

And here a request that is not caught:

...
login(username: string, password: string): Observable<boolean> {

        return this.http.post(environment.baseUrl + '/api/authenticate', JSON.stringify({ username: username, password: password }))
            .map((response: Response) => {
...

Perhaps I have some interference with my second interceptor that should redirect on 401 errors:

import 'rxjs/add/operator/do';
import 'rxjs/add/operator/catch';
import 'rxjs/add/observable/empty';
import 'rxjs/add/observable/throw';
import 'rxjs/add/operator/finally';
import {
    HTTP_INTERCEPTORS, HttpErrorResponse, HttpEvent, HttpHandler, HttpInterceptor,
HttpRequest
} from '@angular/common/http';
import {Injectable} from '@angular/core';
import {Router} from '@angular/router';
import {Observable} from 'rxjs/Observable';

@Injectable()
export class ErrorInterceptor implements HttpInterceptor {

    constructor(private router: Router) {}

    intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
        console.log('Error interceptor at work: ', req.url);

        return next.handle(req)
            .do(event => {
                console.log('error interceptor in success', event);
            })
            .catch(err => {
                console.log('error interceptor in error', err);
                if (err instanceof HttpErrorResponse && err.status === 401) {

                    if (err.url !== '/login') {
                        console.log('redirecting to login...');
                        this.router.navigate(['/login']);
                    }
                }
                return Observable.throw(err);
                // or return Observable.empty();
            })
            .finally(() => {
                console.log('error finally');
            });
    }
}


export const ErrorInterceptorProvider = {
    provide: HTTP_INTERCEPTORS,
    useClass: ErrorInterceptor,
    multi: true,
};

And here is how I integrate them in my app.module:

  providers: [
    AuthGuard,
    AuthenticationService,
    UserService,
    MockBackend,
    BaseRequestOptions,
    GoogleAnalyticsEventsService,
    ErrorInterceptorProvider,
    AuthInterceptorProvider
  ]
2
There can be any problem. Can you reproduce it? Are you using only one interceptor? - yurzui
Could you please set up your project here? - slesh
Yes I can reproduce it. What do you need to know? I'm using a second interceptor to catch errors. Will add this in my edit above - netshark1000
did you fix your problem? i have the same problem ! - Vince

2 Answers

1
votes

I think the problem is actually with your import of HttpClientModule.

See my full answer here: HTTP_INTERCEPTORS only in AppModule

-2
votes

I have found that my issue was that interceptor has to be provided in every module in Angular application, where you want to intercept requests, not just container module.