Angular 6在令牌更新后重制请求之前更改JWT令牌

Posted

技术标签:

【中文标题】Angular 6在令牌更新后重制请求之前更改JWT令牌【英文标题】:Angular 6 change JWT token before remake request after token update 【发布时间】:2019-10-06 17:21:16 【问题描述】:

我在令牌过期时使用 JWT 身份验证结束(后端检查它)我必须调用刷新令牌 API 并重新进行最后一次调用失败,因为令牌过期。 我已经有了拦截器,但我必须在发出请求之前更新身份验证标头,并且我必须等待refreshToken 调用。

intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> 
    const  shouldRetry  = this;
    return next.handle(request).pipe(  
      retryWhen(genericRetryStrategy(
        shouldRetry
      )),

      catchError(err => 
        //401 the token is invalid so I have to refresh it
        if (err.status === 401) 
          this.auth.refreshToken().subscribe(
            (apiResult: SessionTokenResponse) => 
              this.auth.saveToken(apiResult.token);
            ,
            error => this.auth.logout()
          );
          request = request.clone(headers: request.headers.set('Authorization', 'Bearer ' + this.auth.getSessionToken));
          return next.handle(request);
        
        const error = err.error.message || err.statusText;
        return throwError(error);
      ),
    )
  

重新拨打电话是否正确?我如何才能等待refreshToken 的结束?谢谢

编辑:我更新了这段似乎可以工作的代码,我正在测试它

intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> 
const  shouldRetry  = this;
return next.handle(request).pipe(
  retryWhen(genericRetryStrategy(
    shouldRetry
  )),

  catchError(err => 
    //401 the token is invalid so I have to refresh it
    if (err.status === 401) 
      this.auth.refreshToken().subscribe(
        (apiResult: SessionTokenResponse) => 
          this.auth.saveToken(apiResult.token);
          request = request.clone( headers: request.headers.set('Authorization', 'Bearer ' + apiResult.token) );
          next.handle(request).subscribe();
        ,
        err => this.auth.logout()
      );          
    else
      const error = err.error.message || err.statusText;
      return throwError(error);
    
  ),
)

【问题讨论】:

【参考方案1】:

如果我能很好地解决您的问题,您可以使用 async 等待刷新令牌 您可以检查当前令牌的访问权限,如果它在CanActivate 中无效,则刷新它顺便说一句,在每个请求中,它都会检查访问权限以获取令牌,无需在interceptor 中添加额外的代码

在身份验证服务中

     async isAuthenticated()
     const response = await this.auth.refreshToken().toPromise();
     return response;
  

在 CanActivate 中

async canActivate(route: ActivatedRouteSnapshot, state: RouterStateSnapshot) 
    this.authenticated= await this.Service.isAuthenticated();
    if(this.authenticated) 
         this.auth.saveToken(apiResult.token);
         return true;
      
    else
        this.auth.logout();
        // navigate to login


【讨论】:

我必须等待新令牌才能重新拨打电话 不明白是否必须更新令牌我必须管理 401 错误,在您的示例中,您无需此检查即可更新令牌

以上是关于Angular 6在令牌更新后重制请求之前更改JWT令牌的主要内容,如果未能解决你的问题,请参考以下文章

如何在离开页面之前警告用户未保存的表单更改? - 角度 6

防止在 Angular 中多次触发令牌刷新请求

在发出克隆请求之前更新令牌

Angular 6 - 为啥生产构建中缺少承载令牌? (在开发版本中工作正常)

Angular 4 和 OAuth - 拦截 401 响应,刷新访问令牌并重试请求

不记名令牌未添加到 HTTP 请求 - MSAL2 Angular