Узел MongoDB l oop через первую запись коллекции и pu sh ее в массив - PullRequest
0 голосов
/ 13 июля 2020

Я пытаюсь получить список имен пользователей по номеру c имен коллекций. Я создал запрос и, похоже, работает нормально, но он не попадает в массив, поэтому я могу вернуть все данные в качестве ответа для api.

router.get('/chat-logs', async (req, res) => {
  const collections = Object.keys(db.db.collections);

  MongoClient.connect(url, { useUnifiedTopology: true }, function(err, dbm) {
    if (err) throw err;
    var dbo = dbm.db('dbname');
    let collections = dbo
      .listCollections()
      .toArray()
      .then(data => {
        let names = [];
        forEach(data, function(e) {
          let { name } = e;
          if (!isNaN(name)) {
            dbo.collection(name).findOne({}, function(err, result) {
              if (err) throw err;
                names[name] = `${result.first_name} ${result.last_name}`;
            });
          }
        });
        console.log(names)
        res.send(names);
      });
  });
});

как вы можете видеть, я получаю всю коллекцию имена, потому что журналы чата хранятся с соответствующими идентификаторами в виде коллекции, и я просматриваю их и выбираю их последние поля. В конце я пытаюсь вставить sh его в массив names [], чтобы я мог собрать их все и отправить ответ. Проблема в том, что массив остается пустым за пределами области запроса. Я как бы застрял на этом этапе, мне было интересно, есть ли более простой способ получить все коллекции с их последними полями в виде массива, и если нет, то как я могу это исправить?

спасибо

1 Ответ

1 голос
/ 13 июля 2020

См. Node JS Promise.all and forEach

Вы можете сделать что-то вроде этого:

router.get('/chat-logs', async (req, res) => {
  const collections = Object.keys(db.db.collections);

  MongoClient.connect(url, { useUnifiedTopology: true }, function(err, dbm) {
    if (err) throw err;
    var dbo = dbm.db('dbname');
    let collections = dbo
      .listCollections()
      .toArray()
      .then(data => {
        let names = [];
        i = 0;
        data.forEach(function(e) {
          let { name } = e;
          if (!isNaN(name)) {
            dbo.collection(name).findOne({}, function(err, result) {
              if (err) throw err;
              names.push(`${result.first_name} ${result.last_name}`);
              i=i+1;
              if(i>(names.length-1)){
                // all callbacks have finished. 
                console.log(names)
                res.send(names);
              }
            });
          }
        });

      });
  });
});
...