AngularJs 攔截器,攔截請求

問題前述

  在項目中遇到這樣一個問題:javascript

    在Angular項目中,會有不少須要用戶點擊操做的地方,若是用戶點擊過快會產生屢次相同請求,會吃服務器帶寬,若是這是其餘涉及錢有關的操做,這會產生一個致命的問題。對於這個問題,我想到了兩種解決方案:  html

   1. 好比 在點擊一個按鈕操做的時候,咱們經過將這個按鈕 disabled 屬性設置爲 true ,當請求結束後,再設置爲 false ,前端

    代碼:    java

html: 緩存

<div class="btn" ng-click="login()" ng-disabled="is_click">登陸</div>

 

Js:  服務器

$scope.login = function(){
//將按鈕置爲不可點擊狀態
is_click = true; 

//執行http請求操做
$http({
method : method,
params : params,
url : Config.BASE_URL + url
})
.then(function(){
//請求成功,將按鈕置爲可點擊狀態
is_click = false;
})
}

   若是我有不少這樣的操做,就須要寫不少相同的代碼。url

  AngularJs提供了一個攔截器,每次請求在http時,會先到攔截器中。因此,咱們能夠在攔截器中採起處理:spa

  1.首先定義一個參數如:is_click, 在須要處理這個操做的地方經過附加這個參數,這樣可讓咱們去判斷這個操做需不須要去檢測code

  2.若是有,則進行檢測,是否在一秒以內有相同請求(method、url、參數全相同視爲相同請求)htm

  3.若是沒有,則添加到緩存中,若是有,則取消操做

  具體見代碼:

.factory('interceptor', ['$scope', function($scope){
    var requestList = [];    //緩存記錄
    function addRequestList(url){     //插入記錄
    var keepGoing = true;
      angular.forEach(requestList, function (item) {
        if(keepGoing && item.name == url){
          item.time = new Date().getTime();
          keepGoing = false;
        }
      });

      if(keepGoing){
        requestList.push({
          name: url,
          time: new Date().getTime()
        });
      }
    }
    function hitRequestList(url) {    //檢測是否有記錄,並返回時間
    var time = '';
      var keepGoing = true;
      angular.forEach(requestList, function (item) {
        if(keepGoing && item.name == url){
          time = item.time;
          keepGoing = false;
        }
      });
      return time;
    }
     //method,url,data 拼接成 string
    function getRequestKey(data) {
      var key = 'method:' + data.method + ',url:' + data.url + ',data:';
      var str = '';

      //特殊處理
        ...

      return key += str ? str : JSON.stringify(data.params || {});
    }
     var _interceptor = {
          'request': function(req) {
            if (req.params && req.params.is_click) {
              var key = getRequestKey(req);
              var lastTime = hitRequestList(key);      //上次請求時間
              var requesTime = new Date().getTime();   //當前請求時間
              if (lastTime && ((requesTime - lastTime) < 1000)) {
                console.log('----------', '取消此次請求');
                req.method = 'GET';
                req.cache = {
                  get: function () {
                    return null;
                  }
                };
              }
              addRequestList(key);
            }
        return _interceptor
}])        

  最主要的取消請求的代碼: 

 

        req.method = 'GET';
                req.cache = {
                  get: function () {
                    return null;
                  }
                };


總結:
  做爲前端小學生,第一次寫文章,難免有些錯誤的地方,但願你們能夠提出來,感謝。
相關文章
相關標籤/搜索