Я пытаюсь использовать Q для выполнения некоторой работы. Я перебираю и вызываю функцию, которая сохраняет данные в базу данных и возвращает обещание. Как только это будет сделано, мне нужно сделать что-то еще, но Q.all завершается, хотя я вижу, что вызывается каждое разрешение. Я схожу с ума, есть идеи?
Установка:
// save the divisions and then do the division checks
// data.divisions is an array of objects
var promises = [];
data.divisions.forEach(function(dd){
var d = new grpl.division.Division(dd),
p = d.save();
promises.push(p);
});
Q.all(promises)
.then(function(){
// do some other stuff here
// this never actually gets called
}).fail(function(err){
cb(err);
}).done();
А вот d.save()
Division.prototype.save = function(){
var self = this
d = Q.defer();
getPool().getConnection(function(err, db){
if(err){ d.reject(err); return false; }
var fields = {
division_id: self.division_id,
season_id: self.season_id,
title: self.title,
cap: self.cap,
display_order: self.display_order
};
db.query("INSERT INTO division SET ? ON DUPLICATE KEY UPDATE ?", [fields, fields], function(err, result) {
if(err){ d.reject(err); return false; }
d.resolve(true);// this does get resolved for each division
});
});
return d.promise;
}
Я понятия не имею, что не так, но он просто останавливается и, похоже, никогда не разрешал мой вызов Q.all.
ОБНОВЛЕНИЕ Похоже, что первоначальный вызов сохранения будет работать правильно, но последующие вызовы сохранения, похоже, разрешают то же обещание, что и первый вызов. Я обернул тело кода сохранения в переменную функцию, которую я вызвал из сохранения, и она работает, но я не уверен на 100%, почему (прототипное наследование - мой запасной вариант, когда JS действительно меня смущает). Любые объяснения или лучшие способы сделать это?
Division.prototype.save = function(){
var func = function(self){
var d = Q.defer();
d.promise.division_id = self.division_id;
getPool().getConnection(function(err, db){
if(err){ d.reject(err); return false; }
var fields = {
division_id: self.division_id,
season_id: self.season_id,
title: self.title,
cap: self.cap,
display_order: self.display_order
};
db.query("INSERT INTO division SET ? ON DUPLICATE KEY UPDATE ?", [fields, fields], function(err, result) {
if(err){ d.reject(err); return false; }
d.resolve(result);
});
});
return d.promise;
}
return func(this);
}
.save
напрямую без.all
? - person loganfsmyth   schedule 06.06.2014all
, посколькуsave
вызывается независимо отall
, это просто возвращенные промисы изsave
, которые добавляются в массив, над которым работаетall
. Но теперь, когда я говорю, я мог видеть, как он может хранить ссылку на функцию сохранения вместо возвращаемого обещания. Надо будет попробовать, когда вернусь домой. - person aron.duby   schedule 07.06.2014.all
, а не что-то еще? Если вы сделаетеd.save().then(function(){ ... });
, это запустится? - person loganfsmyth   schedule 07.06.2014save
работает, то можете ли вы устранить проблему, чтобы не включать какую-либо логику вашей БД? Ваш пример сейчас довольно большой. - person loganfsmyth   schedule 07.06.2014getPool().getConnection()
иdb.query()
). Сначала вы должны преобразовать обратные вызовы в стиле Node в промисы. Итак, вместо того, чтобы вручную создавать промис с помощьюQ.defer()
, взгляните наQ.denodeify()
или один из подобных вспомогательных методов (Q.nbind
,Q.nfapply
). - person Sergey K   schedule 07.06.2014