letter Q
letter Q

Reputation: 15405

How to return the result of multiple async/await calls in node.js and mongoose

So I have a function that makes a series of async calls to a MongoDB database. I want to return the result when all of the calls are done however the following code isn't doing that.

const getMatchesInfo = async mongoDBUserIds => {
    _.map(mongoDBUserIds, async mongoDBUserId => {
        const user = await UserCollection.findOne({
            _id: mongoDBUserId
        });
        console.log('user.profile.name = ', user.profile.name);

        return user;
    });
};

I call this function in my Node.js API with:

module.exports = app => {
    app.get('/api/matches', requireLogin, async (request, response) => {
        const mongoDBUserIds = request.query.mongoDBUserIds.split(',');
        let matches_info = await getMatchesInfo(mongoDBUserIds); // <=== await here

        console.log('matches_info = ', matches_info);
        response.send(matches_info);
    });
};

What I don't understand is why is matches_info getting printed out before the console.logs inside function getMatchesInfo? I thought the await here was suppose to prevent code below it from running until getMatchesInfo returned. What am I not understanding?

Upvotes: 1

Views: 1216

Answers (1)

Antonio Val
Antonio Val

Reputation: 3340

It's not Mongoose related, asynchronous operations inside _.map() callback are not going to work as you think it will.

Check the explanation in this question, it is about Array#forEach(), but applies as well to your case.

This should work for you:

const getMatchesInfo = async mongoDBUserIds => {
  const users = [];
  for (mongoDBUserId of mongoDBUserIds) {
    const user = await UserCollection.findOne({
        _id: mongoDBUserId
    });
    console.log('user.profile.name = ', user.profile.name);
    users.push(user);
  }
  return users;
};

By the way you were not getting back the result of _.map() in your code.

Upvotes: 4

Related Questions