将Mongoose查询输入数组

时间:2015-11-18 14:31:52

标签: javascript node.js mongoose

我对这段代码有一些问题。 因此,我使用Mongoose从我的数据库中获取数据,然后我想将一段数据推送到一个名为“作者”的数组中。然后单独使用该数据。

我可以访问数据,因为如果我使用console.log()调试它,但是我无法在while循环之外获取该数据。发生了什么?

最后一行以' []'

回应
    while (i < 8) {
        var search = User.find({'twitter.id' : collected[i].author});

        search.exec(function (err, user){
            if (err) return console.error(err);

            var result = (user[0].twitter.username);
            authors.push(result);

        });

        i = i + 1;
    }

    console.log(authors);

2 个答案:

答案 0 :(得分:2)

由于Javascript是异步的,即使循环仍在运行,也会执行console.log(authors)

要在js中处理异步,您可以使用此async模块,它非常强大且易于使用。

---编辑

var _  = require('lodash');
var authors;
User.find({ "twitter.id" : {$in: _.map(collected, 'author')}}).exec()
.then(function(docs) {
    author = docs;
    // Do something

})

我认为你可以这样做,它与@inspired

基本相同

答案 1 :(得分:2)

  

最后一行以&#39; []&#39;

回应

这是因为User.find()async电话。因此,当您在i = 8时退出循环时,您将在数据返回之前点击console.log(authors)

另一个问题

当您只需要进行8调用时,您似乎正在对数据库进行1次单独调用。如果你有一个名为collected的数组,你正在循环。它看起来像这样。

var collected = [
  { author : "23423423"},
  { author : "23423424"},
  { author : "23423425"},
  { author : "23423426"},
];

您可以使用.map功能收集所有Twitter ID。

var twitterIds = collected.map(function(a){return a.author});

现在twitterIds == ["23423423", "23423424", "23423425", "23423426"]

然后,您可以使用$in运算符选择twitter.id的值等于指定数组中任何值的文档。

然后,您可以执行此操作User.find({ "twitter.id" : {$in : twitterIds}});

它将返回一个文档,其中包含您可以操作的所有匹配文档。现在,您已减少为1来电而非8

使用两个选项重构

我会用以下两种方式之一重构代码:

1)返回查询

function search(twitterIds){
   var query = User.find({ "twitter.id" : twitterIds});
   return query;
}

然后您可以这样使用它:

var searchQuery = search(twitterIds);
searchQuery.exec(function(err,users){
  if(err) return console.log(err);
  //do something with users..
  users.forEach(function(user){
  console.log(user.twitter.username);// do something here
  });
}

2)退回承诺

function search(twitterIds){
   var promise = User.find({ "twitter.id" : twitterIds}).exec();
   return promise;
}

然后您可以这样使用它:

var promise = search(twitterIds);
promise.then(function(users){
  //do something...
}).error(function(err){
   console.log(errr);
});

在使用async库之前,我会从这里开始看看是否可以完成工作。