Reputation: 6271
I have to run mongoose query repeatedly within a for loop and once that completes, I want to render a page in express. Sample code given below. Since mongoose runs asynchronously, how can I make the 'commands/new' page to render only once the 'commands' array has been populated within the for loop?
...
...
var commands = [];
for (var index=0; index<ids.length; index++) {
mongoose.model('Command').find({_id : ids[index]}, function (err, command){
// do some biz logic with the 'command' object
// and add it to the 'commands' array
commands[index] = command;
});
}
res.render('commands/new', {
commands : commands
});
...
...
Upvotes: 2
Views: 699
Reputation: 50406
Your basic for
loop here does not respect the callback completion of the asynchronous methods you are calling before executing each iteration. So simply use something that does instead. The node async
library fits the bill here, and in fact for even better methods of array iteration:
var commands = [];
async.each(ids,function(id,callback) {
mongoose.model("Command").findById(id,function(err,command) {
if (command)
commands.push(command);
callback(err);
});
},function(err) {
// code to run on completion or err
})
And therefore async.each
or possibly a variant like async.eachLimit
which will only run a limited number of parallel tasks as set will be your better loop iteration control methods here.
NB The .findById()
method of Mongoose also helps shorten coding here.
Upvotes: 2