Skip to content

拦截器中使用异步操作 #66

@alanhe421

Description

@alanhe421

最近一个项目有这样的需求,在发送请求时,如果没有用户信息,则请求后端拿到用户信息,继续发送该请求。这样的需求,想了下,适合在NG的拦截器这块去做,那么如果实现呢。

实现

auth-service.ts

@Injectable()
export class AuthService {


    constructor(private http: HttpClient) {
    }

    getToken(): string {
        return localStorage.getItem('token');
    }

    removeToken(): void {
        localStorage.removeItem('token');
    }

    logic() {
        return this.http.get('mock-data/user.json').map((res: any) => {
            localStorage.setItem('token', res.token);
            return res;
        });
    }
}

token-interceptor.ts

@Injectable()
export class TokenInterceptor implements HttpInterceptor {
    constructor(public authService: AuthService) {
    }

    intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
        if (request.url === 'mock-data/user.json') {
            return next.handle(request);
        }

        if (this.authService.getToken()) {
            request = request.clone({
                setHeaders: {
                    Authorization: `Bearer ${this.authService.getToken()}`
                }
            });
            return next.handle(request);
        }

        return this.authService.logic().flatMap(() => {
            return next.handle(request).do((event) => {
                    return event;
                }
            );
        });
    }
}

防止死锁

注意,这里一开始有个URL的判断,因为我们下面的情况,需要多请求一次登录,而登录本身的请求,也会走拦截器,所以这里需要加上判断,去掉登录这个请求,否则,登录请求进来,还是会再请求一次登录无限走下去,内存溢出。

相关资料

https://stackoverflow.com/questions/45345354/how-use-async-service-into-angular-httpclient-interceptor

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions