首页 文章

使用http拦截器 - Angular 5 - Ionic 3从离子存储设置默认请求标头

提问于
浏览
3

我正在尝试使用angular 5 new HTTP client在所有请求标头中设置标记值 . 以下是我的代码:

import {Injectable} from '@angular/core';
import {HttpEvent, HttpInterceptor, HttpHandler, HttpRequest} from '@angular/common/http';
import {Observable} from "rxjs/Observable";
import { Storage } from '@ionic/storage';
import {Globals} from '../globals/globals';

@Injectable()
export class Interceptor implements HttpInterceptor {
  token: string;
  constructor(private storage: Storage, private global: Globals){ 
    this.storage.get('token').then((val) => {
      this.token = val;
    });
  }

  intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    console.log(this.token) //undefined "only for first time on app start"
    req = req.clone({
      setHeaders: {
        'Token': this.token,
        'Version': this.global.version,
      }
    });
    return next.handle(req);
  }
}

虽然在请求标头中添加令牌有效,但是有一个不好的例外 . 它不是第一次起作用 . 问题在于js异步性质,req.clone在从存储中获取令牌之前执行 . 因为离子存储器有回报的承诺,所以第一次如何处理这种情况呢?

1 回答

  • 3

    您可以合并异步请求(获取令牌和处理请求)以在令牌准备就绪时执行稍后(而不是在构造函数中获取它):

    // -------------------------------------------------------------------------
    // Please note that I'm using lettable/pipeable operators (RxJS > 5.5.x)
    // https://github.com/ReactiveX/rxjs/blob/master/doc/pipeable-operators.md
    // -------------------------------------------------------------------------
    
    import { Injectable } from '@angular/core';
    import { HttpEvent, HttpInterceptor, HttpHandler, HttpRequest } from '@angular/common/http';
    import { Observable } from "rxjs/Observable";
    import { Storage } from '@ionic/storage';
    import { Globals } from '../globals/globals';
    
    // New imports!
    import { fromPromise } from 'rxjs/observable/fromPromise';
    import { mergeMap } from 'rxjs/operators/mergeMap';
    
    @Injectable()
    export class Interceptor implements HttpInterceptor {
    
      constructor(private storage: Storage, private global: Globals){ }
    
      getToken(): Promise<any> {
        return this.storage.get('token');
      }
    
      intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
        return fromPromise(this.getToken()).pipe(
            mergeMap(token => {
    
                // Use the token in the request
                req = req.clone({
                    setHeaders: {
                        'Token': token,
                        'Version': this.global.version,
                    }
                });
    
                // Handle the request
                return next.handle(req);
            }));
      }
    }
    

相关问题