javascript node.js mongodb promise q

javascript - Problema al devolver los datos recuperados de las consultas de DB llamadas en el bucle



node.js mongodb (1)

Comencemos con la regla general para usar promesas:

Cada función que hace algo asíncrono debe devolver una promesa

¿Qué funciones son estas en tu caso? Es getPrayerInCat , la forEach llamada Prayer.find y Prayer.find .

Hm, Prayer.find no devuelve una promesa, y es una función de biblioteca, por lo que no podemos modificarla. La regla 2 entra en juego:

Cree un contenedor inmediato para cada función que no

En nuestro caso, eso es fácil con los ayudantes de interfaz de nodo de Q :

var find = Q.nbind(Prayer.find, Prayer);

Ahora solo tenemos promesas y no necesitamos más aplazamientos. La tercera regla entra en juego:

Todo lo que hace algo con un resultado asíncrono entra en una devolución de llamada .then

... y devuelve el resultado. ¡Demonios, ese resultado puede ser incluso una promesa si "algo" fuera asíncrono! Con esto, podemos escribir la función de devolución de llamada completa:

function getPrayerCount(data2) { var id = data2.id; return find({prayerCat:id}) // ^^^^^^ Rule 1 .then(function(prayer) { // ^^^^^ Rule 3 if (!prayer) data2.prayersCount = 0; else data2.prayersCount = prayer.length; return data2; // ^^^^^^ Rule 3b }); }

Ahora, tenemos algo un poco más complicado: un bucle. getPrayerCount() repetidamente a getPrayerCount() nos dará múltiples promesas, cuyas tareas asincrónicas se ejecutan en paralelo y se resuelven en un orden desconocido. Queremos esperar a todos ellos, es decir, obtener una promesa que se resuelva con todos los resultados cuando haya finalizado cada una de las tareas.

Para tareas tan complicadas, no intente encontrar su propia solución:

Verifique la API de su biblioteca

Y allí encontramos Q.all , que hace exactamente esto. Escribir getPrayerInCat es muy fácil ahora:

function getPrayerInCat(data) { var promises = data.map(getPrayerCount); // don''t use forEach, we get something back return Q.all(promises); // ^^^^^^ Rule 1 }

Si necesitáramos hacer algo con la matriz que Q.all resuelve, simplemente aplique la Regla 3.

Realizo múltiples consultas mongoDB en bucle. y quiero enviar todos los resultados como una matriz de datos. Pero cuando simplemente uso la devolución para enviar los datos, simplemente devuelve indefinido y no espero los resultados de todas las solicitudes de DB. También intenté usar q.moulde pero el mismo problema.

Código:

var getPrayerInCat = function(data){ var result ; var finalData = []; if(data.length >0){ data.forEach(function(data2){ var id= data2.id; Prayer.find({prayerCat:id},function(err,prayer){ var deferred = Q.defer() if (err) { // ... console.log(''An error has occurred''); // res.send(err); result= finalData = err } else { if(!prayer){ // console.log(data2.id+''--0''); data2.prayersCount = 0; result = deferred.resolve(finalData.push(data2)) } else { // console.log(data2.id+''--''+prayer.length); data2.prayersCount = prayer.length; // console.log(prayer) result = deferred.resolve(finalData.push(data2)) } // else for data forward } deferred.promise; }) // deferred.resolve(finalData); }) /*if(finalData.length > 0) { return finalData;}*/ } }

finalData se devuelve indefinido.