0

I am new to JS. here is my function, so when I use this, it will return an empty list.

if I replace resultArray.push(result); with console.log(result); it will correctly show me the result.

I am expecting to see the function return the query result inside a list.

function queryMongo (key) {

    var url = "mongodb://user:pw/task?replicaSet=bdb";
    var resultArray = [];

    // connect to the mongoDB
    MongoClient.connect(url, { useUnifiedTopology: true }, function(err, db) {
        if (err) throw err;
        var dbo = db.db("task");
        var query = { 'device' : key };
        var cursor = dbo.collection('commands').find(query);
        cursor.forEach(function(result){
            if (err) throw err;
            resultArray.push(result);
        }, function(){
            db.close();
        })
    });
    return resultArray;
}

1
  • 2
    There isn't actually a question. Please try reformulating your message to let the community know what you actually expect from them and also removing "please help me" as this doesn't add value to your issue. I would also invite you making it nicer to read by using the code formatting feature. Commented Mar 25, 2020 at 0:22

2 Answers 2

1

As shown in here one way would be to get the whole dataset at once:

async function queryMongo(key) {
  var url = 'mongodb://user:pw/task?replicaSet=bdb'

  // connect to the mongoDB
  return new Promise(function (resolve, reject) {
    MongoClient.connect(url, { useUnifiedTopology: true }, function (err, db) {
      if (err) throw err
      var dbo = db.db('task')
      var query = { device: key }
      // Fetch all results
      dbo
        .collection('commands')
        .find(query)
        .toArray(function (err, items) {
          if (err) {
            return reject(err)
          }
          resolve(items)
          db.close()
        })
    })
  })
}

async function doWork() {
  // without "async" keyword it's not possible to "await" the result
  console.log(await queryMongo('some-key'))
}

doWork();

Please take following advices into consideration:

  1. Don't connect/disconnect at each function call aside if you're performing queryMongo() once in a while
  2. The reason your code was not working is because you were returning the result before the async call was actually finished. Hence when doing queryMongo() result was straightly []. Indeed, establishing the connection to mongo and performing the query takes "time" and NodeJS will continue performing code execution while this is happening. I would advise to read a bit around the event loop to understand this mechanic a bit better.
Sign up to request clarification or add additional context in comments.

Comments

1

I think that the main problem is that all db calls are asynchronous. You can't just return the value, you can pass to a callback or return Promise.

const MongoClient = require('mongodb').MongoClient;

function queryMongo(key, callback) {
  const url = 'mongodb://localhost:27017';

  MongoClient.connect(url, { useUnifiedTopology: true }, function(err, db) {
    if (err) throw err;
    const dbo = db.db('tasks');
    const query = { device: key };

    dbo
      .collection('commands')
      .find(query)
      .toArray((err, doc) => {
        if (err) throw err;
        db.close();
        callback(doc);
      });
  });
}

queryMongo(12, doc => {

  /* do something */
  console.log(doc);
});

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.