2015-06-23 30 views
2

我從網上覆制了以下代碼以使用JWT授權,但它不起作用。特別是$location.path命令沒有影響 - 重定向不會發生。我也試過$state.go,但是這導致了更大的錯誤。我不完全明白$q這裏指的是什麼,而不是什麼等待承諾放鬆,但是問題是$location.path沒有讓用戶回到登錄屏幕(下面關於$state變化的提議也不是)。

$httpProvider.interceptors.push(function($q, $location, $localStorage) { 
     return { 
      'request': function (config) { 
       config.headers = config.headers || {}; 
       if ($localStorage.token) { 
        config.headers.Authorization = 'Bearer ' + $localStorage.token; 
       } 
       return config; 
      }, 
      'responseError': function(response) { 
       if(response.status === 401 || response.status === 403) { 
        console.log("app.js: httpInterceptor caught authorisation status response"); 
        delete $localStorage.token; 
        $location.path('/'); // to login page 
        // $state.go('login'); 
       } 
       return $q.reject(response); 
      } 
     }; 
    }); 
} 

爲了測試,我發送創建一個服務器錯誤的消息,趕在路上devtools回來,然後手動設置response.status = 403。重定向被明確解析,但不會導致重定向。我可以看到登錄屏幕放回到屏幕上,但是立即被另一個視圖覆蓋。

這是工廠$ http ajax請求。 我在這裏使用的deferred$q是否可能干擾攔截器中的?

$http(httpObj) 
    .success(function (response) { // returns 0: mongo resto data, 1: wpserver report 
     console.log("%s succesful, response: %s", method, response); 

     if (!updateNotAdd) { 
      Restos.data.restos.push(response[0]); // add to local copy of data 
     } else { 
      // replace existing entry with new information 
      var idxToReplace = _.findIndex(Restos.data.restos, function(r) { 
       return r.qname === resto.qname; 
      }); 
      // copy over all data from editor model to database 
      _.assign(Restos.data.restos[idxToReplace], resto); 
     } 

     var response = { 
      success: true, 
      id: response[0]._id, 
      message: response[1] 
     }; 

     $rootScope.$broadcast("ajaxresponse", response); 
     deferred.resolve(response); 
    }) 
    .error(function (msg) { 
     // console.log(msg); 
     var response = { 
      success: false, 
      message: msg 
     }; 
     $rootScope.$broadcast("ajaxresponse", response); 
     deferred.resolve(response); 
    }); 

    return deferred.promise; 
+0

看起來像你需要在'$ location.path('/');'然後執行'$ scope。$ apply()' –

+0

'之後運行digest循環,因爲'$ scope'不能從'.config'方法 –

+0

ohh..thats我的壞...你應該這樣做'$ rootScope'..for獲得'$ rootScope'你需要在函數中添加'$ injector'依賴項然後在你的'responseError'函數中可以使用'var rootScope = $ injector.get('$ rootScope'); $ location.path( '/'); rootScope。$ apply()' –

回答

3

在這裏你不應該有一個利用ui-router的問題。您需要使用$injector服務獲取有關$state服務的參考。遵守以下變化...

$httpProvider.interceptors.push(function($q, $location, $localStorage, $injector) { 
     return { 
      'request': function (config) { 
       config.headers = config.headers || {}; 
       if ($localStorage.token) { 
        config.headers.Authorization = 'Bearer ' + $localStorage.token; 
       } 
       return config; 
      }, 
      'responseError': function(response) { 
       if(response.status === 401 || response.status === 403) { 
        console.log("app.js: httpInterceptor caught authorisation status response"); 
        delete $localStorage.token; 
        $injector.get('$state').go('login'); 
       } 
       return $q.reject(response); 
      } 
     }; 
    }); 
} 

您遇到被循環依賴由於UI路由器注入$http$TemplateFactory引起了更大的問題 - 導致循環引用$http$httpProvider當您嘗試注入$state(這還沒有出現在你的interceptors注射簽名反正)

+0

,但是也可以重定向。我已經在原始問題中添加了更多代碼,以查看是否存在其他干擾 –

+0

@SimonH是否碰到了'console.log(「app.js:...'?..嘗試交換'.go()' (''state')。transitionTo('login');' – scniro

+0

是的,'console.log'被命中,但重定向沒有發生,服務器錯誤通過回傳給原始頁面第二個代碼段中的'.error'函數 –

0

不知道你是否要使用,但可能這會重定向:

$window.location.href = url;