加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 综合聚焦 > 服务器 > 安全 > 正文

angularjs – 拦截器中的无限循环

发布时间:2020-12-17 17:38:50 所属栏目:安全 来源:网络整理
导读:我已经建立了一个使用API??的AngularJS网站.此API提供的功能很少,如身份验证(Oauth). 当API返回401错误时,表示access_token已过期,需要使用refresh_token刷新. 我在AngularJS中创建了一个拦截器.其目标是检查API返回的结果是否为401错误,如果是这种情况,则必
我已经建立了一个使用API??的AngularJS网站.此API提供的功能很少,如身份验证(Oauth).

当API返回401错误时,表示access_token已过期,需要使用refresh_token刷新.

我在AngularJS中创建了一个拦截器.其目标是检查API返回的结果是否为401错误,如果是这种情况,则必须刷新令牌,然后处理先前被拒绝的请求.

问题是拦截器创建了一个无限循环.在初始请求的第二次失败之后,它应该停止但它不会.

angular.module('myApp')
.factory('authInterceptor',function ($rootScope,$q,$window,$injector) {

  return {

    // If the API returns an error
    'responseError' : function(rejection) {

      // If it's a 401
      if (rejection.status == 401) {

        var deferred = $q.defer();

        $injector.get('$http').post('http://my-api.local/api/oauth/token',{
          grant_type    : 'refresh_token',client_id     : 'id',client_secret : 'secret',refresh_token : $window.sessionStorage.refresh_token
        },{
          headers : {
            'Content-Type'  : 'application/x-www-form-urlencoded'
          },transformRequest  : function(obj) {
            var str = [];
            for(var p in obj)
            str.push(encodeURIComponent(p) + "=" + encodeURIComponent(obj[p]));
            return str.join("&");
          }
        })
        // New token request successfull
        .success(function(refreshResponse) {

          // Processing the failed request again (should fail again because I didn't saved the new tokens)
          $injector.get('$http')(rejection.config).success(function(data) {

            deferred.resolve(data);

          })
          .error(function(error,status) {

            deferred.reject();

          });

          return deferred.promise();

        })
        // New token request failure
        .error(function(error,status) {

          deferred.reject();
          // $location.path('users/login');

          return;

        });

      }
      // If it's another errorenter code here
      else
        return rejection;

    }

  }

});

所以这段代码:

>第一个请求失败时启动
>刷新令牌
>重试请求但又失败了(< - 我只是想让它停在这里)
>刷新令牌
>重试请求但又失败了
>刷新令牌
>重试请求但又失败了
>等……

解决方法

我在我的应用程序中进行了此操作.您的刷新请求需要包含一个config / header变量,如skipIntercept:true.然后,当您将此作为失败的响应进行拦截时,可以检查rejection.config.skipIntercept变量.如果是真的,你直接进入$q.reject(拒绝).

你在哪里:

if (rejection.status == 401) {

将其更改为:

if (rejection.status == 401 && !rejection.config.skipIntercept) {

然后在上面:

headers : {
        'Content-Type'  : 'application/x-www-form-urlencoded'
     },

你需要添加:

skipIntercept: true,headers: {
        'Content-Type'  : 'application/x-www-form-urlencoded'
     },

PS.你可以使用there’s an existing solution.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读