2015-12-11 3 views
0

Я пытаюсь вызвать функцию поиска петли внутри цикла for, передавая значение из итерации в функцию loopback. Основная проблема кода может быть представлена ​​в следующем:Strongloop prom inside loop

for (var a = 0; a < $scope.countries.length; a++) { 
    $scope.getEmFacPurElec($scope.countries[a], 'ton/kWh', 'CO2e').then(function(result) { 
    emFacPurElecToUse = $scope.emFacPurElecs; 
} 

А вот функция вызывается:

$scope.getEmFacPurElec = function (country, unit, ghgType) { 
    var defer = $q.defer(); 
    $scope.emFacPurElecs = []; 

    $scope.emFacPurElecs = Country.emFacPurElecs({ 
     id: country.id, 
     filter: { 
       where: { 
         and: [ 
          {unit: unit}, 
          {ghgType: ghgType} 
          ] 
         } 
       } 
    }); 

    defer.resolve('Success getEmFacPurElec'); 
    return defer.promise; 
};    

Проблема заключается в том, что функция замыкания на себя обещание называется, а затем вернулся неопределенными, который означает, что он переходит к следующей итерации цикла for, прежде чем получить значение для присвоения emFacPurElecToUse. Мне нужно сделать еще несколько расчетов с этой переменной для этой страны, прежде чем переехать в следующую страну.

Я рассмотрел использование $ q.all в качестве возможного решения, а также используя array.map в соответствии с http://pouchdb.com/2015/05/18/we-have-a-problem-with-promises.html (ошибка Rookie # 2: WTF, как использовать forEach() с обещаниями?), Но я просто не могу выяснить, как собрать все это вместе, чтобы заставить его работать. Должен ли я использовать forEach вместо этого?

Я также видел эту ссылку angular $q, How to chain multiple promises within and after a for-loop (наряду с другими подобными), но у меня нет нескольких обещаний, которые мне нужно обрабатывать внутри цикла for. Мне нужно получить значение одной emFacPurElecs для этой страны, выполнить некоторую работу с ней, а затем перейти к следующей стране. Я чувствую, что я близок, но я просто не могу понять, как я буду кодировать эту конкретную функциональность. Любая помощь приветствуется.

+0

Если вы в конечном итоге думать о замене Q с другой библиотекой обещает в Угловом, вы можете рассмотреть https://github.com/mattlewis92/angular-bluebird-promises, поскольку это то, что я использовал для использования метода 'map()' bluebird для usecase, аналогичного тому, который вы описали. Ссылка: http://bluebirdjs.com/docs/api/promise.map.html – pulkitsinghal

ответ

0

Мне кажется, что у вас есть несколько обещаний для обработки внутри цикла for, поскольку вы говорите: «Мне нужно сделать еще несколько расчетов с этой переменной для этой страны, прежде чем переходить в следующую страну». Все это должно быть сделано в предложенной мной цепочке обещаний - calcEmFacPurElec.

$scope.calcEmFacPurElec = function (country, unit, ghgType) { 
    $scope.getEmFacPurElec(country, unit, ghgType).then(function(countryEmFacPurElecs) { 
    // do something with countryEmFacPurElecs 

    return countryEmFacPurElecs; 
} 

$scope.getEmFacPurElec = function (country, unit, ghgType) { 
    var defer = $q.defer(); 

    defer.resolve(Country.emFacPurElecs({ 
     id: country.id, 
     filter: { 
       where: { 
         and: [ 
          {unit: unit}, 
          {ghgType: ghgType} 
          ] 
         } 
       } 
    }); ); 
    return defer.promise; 
};  

Надеемся, что это указатель в правильном направлении!

Если вы хотите выполнить цепочку обещаний на множестве элементов, то, как вы уже определили, Promise.all (используя любые обещания, которые вам нужны) - это то, что вы хотите. .all занимает в массиве Promises, поэтому в вашем цикл вы можете сделать:

var promises = []; 
for (var a = 0; a < $scope.countries.length; a++) { 
    promises.push($scope.calcEmFacPurElec($scope.countries[a], 'ton/kWh', 'CO2e')); // new promise chain that does all of the work for that country 
} 

$q.all(promises).then(function(arrayofCountryEmFacPurElecs) {console.log('all countries completed')}); 
+1

Спасибо, Конрадж. Извините за поздний ответ. Я был занят какой-то другой работой, потом в отпуске, потом заболел (uggh). Ваш ответ полезен, и я работаю над решением на своем конце, но не получил его. Я попытаюсь опубликовать jsfiddle с конкретной функциональностью, которую я пытаюсь достичь в ближайшие дни, если я не смогу ее получить. Возможно, вы сможете помочь мне завершить решение таким образом. Еще раз спасибо. – Mitch

+0

@Mitch Рад, что это было полезно - с удовольствием попробуем и помогаем, когда у вас есть что-то более конкретное. Не забывайте, что вы можете продвигать полезные ответы, а также отмечать их как правильные ;-) – conradj