2013-12-18 24 views
3

我有一个Angular应用程序,其视图通过$ scope引用更新为由工厂单例显示的某些模型和状态对象。在初始化期间,或者在视图内的某些操作中,工厂必须进行多个AJAX调用(使用Restangular),然后等待所有承诺解决后再更新其状态和模型属性。在对未来的数据采取适当的副作用之前,如何等待多个期货得到解决?使用Restangular在Angular中协调多个AJAX调用

例如显示加载微调器或模型属性的div和根据状态刷新此属性的按钮。

<div ng-controller="MyCtrl"> 
    <div ng-if="state.isLoading" class="loading-animation"></div> 
    <div ng-if="!state.isLoading"> 
     <span ng-bind-template="Property: {{model.property}}"></span> 
     <button ng-click="refresh()">Refresh</button> 
    </div>  
</div> 
App.controller('MyCtrl', ['$scope', 'MyFactory', function('$scope', 'Factory') { 
    $scope['model'] = Factory['model']; 
    $scope['state'] = Factory['state']; 
    $scope.refresh = function() { 
     Factory.init(); 
    }; 
}]) 
.factory('MyFactory', ['restangular', function('Rest') { 
    var Factory = { 
      model = { 
       property: null 
      }, 
      state = { 
       isLoading = false; 
      } 
     }; 

    Factory.init = function() { 
     Factory['state']['isLoading'] = true; 

     var promise1 = Rest.one('first').get(); 
      promise2 = Rest.one('second').get(); 

     // Resolve both promises. 
     // Only when both promises are done, 
     //  update model.property based on data returned and relevant logic. 
     // Toggle isLoading state when finalized. 
    } 

    return Factory;  
}]) 
.run(['MyFactory', function(Factory) { 
    Factory.init(); 
}]); 

什么我遇到的麻烦是如何实现Factory.init的注释部分()。我知道我可以使用Angular的$ q,但是我对延迟对象不太熟悉,我发现$ q上的Angular文档有点混乱。

回答

9

我认为$q.all()是你想要的。这:

将多个承诺组合成一个单一的承诺,当所有的输入承诺解决时解决。 1

未经测试的例子:

var promises = [ 
    Rest.one('first').get(), 
    Rest.one('second').get() 
]; 

$q.all(promises).then(function (results) { 
    var resultOfFirstPromise = results[0], 
     resultOfSecondPromise = results[1]; 
    // update model.property based on data returned and relevant logic. 
}); 
+0

谢谢,这个作品! – SirTophamHatt

+0

对我来说也很有帮助的是使用关联数组。我可以选择使用按键添加承诺,并检查按键以在模型上触发不同的副作用。 – SirTophamHatt

+0

我面对的这个问题是,如果我有一个.then在我的控制器它是抛出未定义 – alyn000r