如何从拦截器中排除登录、注册等服务Angular 5、HttpClient

How to exclude some services like login, register from interceptor Angular 5, HttpClient

我想使用拦截器排除一些服务。

app.module.js

providers: [
    UserService,
    RolesService,
    {
        provide: HTTP_INTERCEPTORS,
        useClass: TokenInterceptor,
        multi: true
      },
],

Login.service.ts

return this.httpClient.post(this.appUrl + '/oauth/token', body.toString(), { headers, observe: 'response' })
.map((res: Response) => {
  const response = res.body;
  this.storeToken(response);
  return response;
})
.catch((error: any) => {
  ErrorLogService.logError(error);
  return Observable.throw(new Error(error.status));
  });
}

不仅要根据要求在评论中给出答案 ;-)

要从拦截器中排除某些服务(甚至不同组件中使用的相同服务),最好将您的应用程序拆分为多个模块,并仅在需要的模块中提供拦截器。例如,在登录或进入管理区域后。

甚至可以使用 @Component 声明的 providers 属性 为单个组件提供拦截器。

虽然#Fussel 的回答(以上)有效,但在每个组件模块中包含拦截器服务通常不是好的做法。这是违反直觉和适得其反的。我们希望拦截器在一个地方并为所有 http 请求工作。 一种方法是根据 url.

在 intercept() 函数中排除 header 绑定
intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
const re = /login/gi;
// Exclude interceptor for login request:
if (req.url.search(re) === -1 ) {
  req = req.clone({
    setHeaders: {
      Authorization: `Bearer ${localStorage.getItem('authToken')}`
    }
  });
}
return next.handle(req);

}

我遇到了类似的问题。一旦实施了拦截器,无论如何都会捕获所有 http 请求。它在我的代码中关于我是否拥有访问令牌。如果我没有比拦截器令牌参数必须设置为“”(空字符串)。比一切顺利。 在拦截器 fn 代码中,它看起来像这样:

       intercept(
          request: HttpRequest<any>,
          next: HttpHandler**strong text**
       ): Observable<HttpEvent<any>> {

        //how to update the request Parameters
        **let token : string;
        let currentUser : any = JSON.parse(localStorage.getItem('currentUser'));
        if (currentUser){
            token = currentUser.access_token;
        }else{token = ""}**

        console.log("Token dobavljen sa localStorage.getItem:   ", token);
        if (token) {
            request = request.clone({ headers: request.headers.set('Authorization', 'Bearer ' + token) });
        }

        if (!request.headers.has('Content-Type')) {
            request = request.clone({ headers: request.headers.set('Content-Type', 'application/json') });
        }

        request = request.clone({ headers: request.headers.set('Accept', 'application/json') });

        //logging the updated Parameters to browser's console
        console.log("Before making api call : ", token);

        return next.handle(request).pipe(
            tap(
                event => {
                    //logging the http response to browser's console in case of a success
                    if (event instanceof HttpResponse) {
                    console.log("api call success :", event);
                    }
                },
                error => {
                    //logging the http response to browser's console in case of a failuer
                    if (event instanceof HttpResponse) {
                    console.log("api call error :", event);
                    }
                }
            )
        );
    //}
}

我也必须解决这个问题。 划分模块对我来说非常昂贵。 当你有几个点需要 "jump" 拦截器

时,#DragoRaptor 解决方案不适合

我的解决方案是非正统的,但也许对其他人有用。

它仅包含:

  1. 请求中再包含一个参数
  2. 在拦截器中检查这个参数
  3. 删除参数

调用示例[​​=32=]

    public searchPersons(term: string): Observable<any> {
       return this.http.get('person/', { params: { dni: term, spinner: 'no' } });
    }

拦截器示例

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

// check if you have the parameter 'spinner'
    const spinner = request.params.get('spinner');
    if (spinner && spinner === 'no') {

// remove parameter
      request.params.delete('spinner');

// jump the interceptor
      return next.handle(request);
    }

// Execute interceptor

  }
}

您可以为此使用 HttpBackend。示例如下

import { Injectable } from '@angular/core';
import { HttpClient, HttpBackend } from '@angular/common/http';

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

 private httpClient: HttpClient;
  constructor( handler: HttpBackend) { 
     this.httpClient = new HttpClient(handler);
     }

   fetchInsta(username) {
      return new Promise((resolve, reject) => {
         this.httpClient.get(`https://www.instagram.com/${username}/?__a=1`)
          .subscribe((response: any) => {
           resolve(response);
             },reject);
               })
              }
          }

我遇到了同样的问题,我是这样解决的:

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

// You can retrieve the url or a part in order to filter them
       if (request.url.slice(0, 20) != 'https://site.to.exclude') {
      request = request.clone({
          setHeaders: {
             'content-type': 'application/json',
            // or your header specific add to the interceptor
          }
        });
      }
     else {
//  interceptor does not add specific header
      return next.handle(request)
      }
   }