如何最大限度地减少收集Angular JS中所有承诺的延迟

时间:2015-01-15 09:21:34

标签: angularjs promise angularjs-service angular-promise

请参阅下面的代码。在'for'循环中,在每次迭代中,我正在进行Ajax调用并将promises推送到数组中并使用$ q.all解析所有这些promise。但它导致延迟,因为我需要等到所有承诺在'for'循环中收集,然后在所有承诺可用之后我需要在$ q.all中逐个解决它们。

var promises = [];

for (var i = 0; i < dashboardslayoutArray.length; i++) {
    dashboardData.dashletteBeansList = [];
    dashboardData.dashletteBeansList[0] = dashboardslayoutArray[i];

    var dashlettePromise = DashboardsDataService.getTabDetails(dashboardData);
    promises.push(dashlettePromise);
}

$q.all(promises)
    .then(function(data) {
        // all promises were resolved here
    });

相反,我想要做的是,在'for'循环中尽快解决它的承诺,而不将其推入$ prom.all中使用的'promises'。有点像,

for (var i = 0; i < dashboardslayoutArray.length; i++) {
    dashboardData.dashletteBeansList = [];
    dashboardData.dashletteBeansList[0] = dashboardslayoutArray[i];

    var dashlettePromise = DashboardsDataService.getTabDetails(dashboardData);

    dashlettePromise.then(function(data) {
        ...
    }, function(error) {
        alert(error);
    });
}    

但这不符合预期。这里第二个承诺结果影响第一个承诺结果等。有没有解决这个问题?

根据@Benjamin Gruenbaum的建议,我已将其更改为

angular.forEach(dashboardslayoutArray, function(dashboardslayout) {
    dashboardData.dashletteBeansList = [];
    dashboardData.dashletteBeansList[0] = dashboardslayout;

    var promise = DashboardsDataService.getTabDetails(dashboardData);

    promises.push(promise);

});

但是我怎么能在这里减少延迟?

@Benjamin Gruenbaum,我在下面总结了我的问题:

var promises = [];
angular.forEach(dashboardslayoutArray, function(dashboardslayout) {
    dashboardData.dashletteBeansList = [];
    dashboardData.dashletteBeansList[0] = dashboardslayout;

    var promise = DashboardsDataService.getTabDetails(dashboardData);

    promises.push(promise);

});

$q.all(promises)
    .then(function(allData) {

        allData.forEach(function(data) {

            for (var dashVar = 0; dashVar < data.tabDetails.length; dashVar++) {
                var dashletteId = data.tabDetails[dashVar].dashletteId;
                var axisType = data.tabDetails[dashVar].axisType;
                // ...   draw c3 chart ...
            }
        });
    });

我需要进行多次Ajax调用,所以我使用了上面的方法,它运行得很好。这里我所有的Ajax调用结果都是独立的,这些都不依赖于其他结果。使用从每个Ajax调用返回的数据,我使用Angularjs C3指令绘制图表。

但我面临的问题是延误。要绘制四个C3图表,我需要使用$ q.all进行四次ajax调用,只有在所有四个Ajax调用完成(已解决或拒绝)后才能开始绘制C3图表。相反,我想做的是,很快任何一个Ajax调用完成(解决或拒绝),我想开始根据特定Ajax调用的结果绘制C3图表。所以我使用了以下方法来避免排队所有承诺的延迟。

angular.forEach(dashboardslayoutArray, function(dashboardslayout) {
    dashboardData.dashletteBeansList = [];
    dashboardData.dashletteBeansList[0] = dashboardslayout;

    var promise = DashboardsDataService.getTabDetails(dashboardData);

    promise.then(function(data) {

        for (var dashVar = 0; dashVar < data.tabDetails.length; dashVar++) {
            var dashletteId = data.tabDetails[dashVar].dashletteId;
            var axisType = data.tabDetails[dashVar].axisType;
            // ...   draw c3 chart ...
        }
    }, function(error) {
        alert(error);
    });

});

我的最后一个问题是,我在promise.then(function (data)内使用angular.forEach(dashboardslayoutArray , function(dashboardslayout)以避免延误是否正确?这种方法有什么潜在的问题吗?我希望,我已经清楚地表达了我的问题,如果不是,请让我知道,我会尽力使用。

1 个答案:

答案 0 :(得分:1)

  

我的最后一个问题是,是否正确使用promise.then(angular(data)在angular.forEach(dashboardslayoutArray,function(dashboardslayout)中)以避免延迟?

是的,这正是你应该做的。 $q.all()允许您在完成一整套承诺后执行某些操作。由于这与您想要做的相反,$q.all()不适合这里的工作。

你从未在第二个代码示例中向我们展示then()中的内容,但是假设你说&#34;第二个承诺结果影响第一个承诺结果等等#34; ,Benjamin Gruenbaum的怀疑很可能是正确的,并且导致问题的是i循环变量。切换到.forEach()会修复此问题。