在继续使用angular.forEach循环之前,如何等待$ http响应

时间:2014-03-28 17:52:01

标签: angularjs

我正在为循环中的每个项目发出AJAX请求,结束REST服务一次只能执行一个请求,因此我需要循环等待每个请求完成,然后继续下一个。我该怎么做?

作为参考,终端服务正在DynamoDB表上执行更新任务 - 一次只能修改一个表因此我要求等到我在继续之前得到响应。我可以将它们全部发送到服务器,然后在那里处理,尽管这使得每次更新完成时很难收到反馈。

angular.forEach($scope.someArray,
  function (value) {

      var postdata = {
        bla: value
      };

      $http.post('/some_url', postdata)
        .then(
        function(result) {
          console.log("Success.");
        },
        function(data) {
          console.log("Failure.");
        }
      );

  }
);

2 个答案:

答案 0 :(得分:10)

你真的需要forEach吗?我不会使用它并去寻找类似的东西:

function req(arr) {
  if (angular.isArray(arr) && arr.length > 0) {
    var postdata = {
      bla: arr[0]
    };
    $http.post('/some_url', postdata)
      .then(
      function(result) {
        console.log("Success.");
        arr.shift();
        req(arr);
      },
      function(data) {
        console.log("Failure.");
        // if you want to continue even if it fails:
        //arr.shift();
        //req(arr);
      }
    );
  }
}
req($scope.someArray);

答案 1 :(得分:4)

如果你真的必须一次提出一个请求(你确定没有更高效的替代方案吗?),那么你将不得不使用Angular.forEach以外的其他东西。

这样的事情(你需要注入$q):

function doWhateverWithAll(someArray) {
  // Mark which request we're currently doing
  var currentRequest = 0;
  // Make this promise based.
  var deferred = $q.deferred();
  // Set up a result array
  var results = []
  function makeNextRequest() {
    // Do whatever you need with the array item.
    var postData = someArray[currentRequest].blah;

    $http.post('some/url', postData)
    .then( function (data){
      // Save the result.
      results.push(data);
      // Increment progress.
      currentRequest++;
      // Continue if there are more items.
      if (currentRequest < someArray.length){
        makeNextRequest();
      }
      // Resolve the promise otherwise.
      else {
        deferred.resolve(results);  
      }  
    });
    // TODO handle errors appropriately.
  }
  // return a promise for the completed requests
  return deferred.promise;
}

然后,在您的控制器/服务中,您可以执行以下操作:

doWhateverWithAll($scope.someArray)

.then(function(results){
  // deal with results.
});