API响应为401时,HTTP Interceptor不会注销用户

时间:2019-06-17 21:29:48

标签: angular angular-http-interceptors

我已经实现了Angular HTTP拦截器,我面临的问题是使令牌失效并单击导航栏的任何组件时,我的服务从API网关返回401 ...这应该注销用户,但是, HTTP状态日志类似于:{type:0},并且会话仍保留在本地存储中,因此用户必须将其删除并尝试重新登录,您能否分享一些见解,我的方法以及如何从中捕获错误401。 Angular 5应用程序中的服务响应。这是我的实现:

import { HttpInterceptor, HttpRequest, HttpHandler } from '@angular/common/http';
import { Subject, Observable } from 'rxjs';
import { Injector, Injectable } from '@angular/core';
import 'rxjs/add/operator/do';
import { Router } from '@angular/router';
import 'rxjs/add/operator/do';
import 'rxjs/add/operator/catch';
import 'rxjs/add/observable/empty';
import { AuthenticationService } from './authentication.service';

@Injectable()

export class TokenInterceptor implements HttpInterceptor {
refreshTokenInProgress = false;

tokenRefreshedSource = new Subject();
tokenRefreshed$ = this.tokenRefreshedSource.asObservable();

constructor(
private injector: Injector,
private router: Router,
private authService: AuthenticationService
) { }

addAuthHeader(request) {
console.log('add auth header');
const authHeader = this.authService.getAccessToken();
if (authHeader) {
return request.clone({
setHeaders: {
'Authorization': 'Bearer ' + authHeader
}
});
}
return request;
}

refreshToken() {
if (this.refreshTokenInProgress) {
return new Observable(observer => {
this.tokenRefreshed$.subscribe(() => {
observer.next();
observer.complete();
});
});
} else {
return this.authService.refresh()
.do(() => {
console.log('this has been treated');
this.refreshTokenInProgress = false;
this.tokenRefreshedSource.next();
});
// }
}
}
intercept(request: HttpRequest<any>, next: HttpHandler): Observable<any> {
this.authService = this.injector.get(AuthenticationService);


// Handle request
request = this.addAuthHeader(request);

// Handle response
return next.handle(request).do((data) => {

console.log('HANDLE RESPONSE', data);

return this.refreshToken()
.do((token) => {
request = this.addAuthHeader(request);
return next.handle(request);
})
.catch(() => {
this.authService.logout();
console.log('observable', Observable.empty());
return Observable.empty();
});
});
}
}

1 个答案:

答案 0 :(得分:0)

为此创建另一个拦截器

import { HttpErrorResponse, HttpEvent, HttpHandler, HttpInterceptor, HttpRequest } from "@angular/common/http";
import { Injectable } from "@angular/core";
import { Observable } from "rxjs/Rx";
import { Router } from "@angular/router";
import { tap } from "rxjs/internal/operators";

@Injectable()
export class UnAuthorizedInterceptor implements HttpInterceptor {
  constructor(private router: Router) { }
  intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    return next.handle(request).pipe(tap(() => { },
      (err: any) => {
        if (err instanceof HttpErrorResponse) {
          if ((err.status === 401) || (err.status === 403)) {
            // do whatever you wants here 
            // clear localstorage ...
            // redirect to login page
          } else {
            return;
          }
        }
      }));
  }
}

然后将{ provide: HTTP_INTERCEPTORS, useClass: UnAuthorizedInterceptor, multi: true }添加为app.module.ts文件中的提供者