如何从MongoDB中的另一个数组中搜索一个数组?

时间:2016-10-29 18:27:23

标签: javascript arrays node.js mongodb express

我有一个users表,它具有以下数据结构:

[{
    userID: 0,
    username: 'test0',
    petsForSale: [
        { type: 'fish' },
        { type: 'cats' }
    ],
    seekingPets: [
        { type: 'dogs' },
        { type: 'birds' }
    ]
},
{
    userID: 1,
    username: 'test1',
    petsForSale: [
        { type: 'guinea pigs' },
        { type: 'dogs' },
        { type: 'hamsters' }
    ],
    seekingPets: [
        { type: 'ferrets' }
    ]
}]

我尝试执行GET,根据petsForSaleseekingPets返回匹配的用户。例如,如果用户正在销售dogs,则会在dogsseekingPets的任何用户的匹配结果列表中显示这些结果。我非常接近,到目前为止我的路由器代码:

router.get('/:id/findmatches', function(req, res) {
  var db = req.db;
  var collection = db.get('users');
  var uid = req.params.id;

  //var seeking_pets = collection.find({ userID: uid }, { seekingPets: 1 });
  //var seeking_pets = collection.find({ userID: uid }, { seekingPets: { type: 1 }});
  var seeking_pets = [ 'dogs', 'birds' ]; // *Hard-coded is the only way I can get it to work

  collection.find({ petsForSale: { $elemMatch: { type: { $in: seeking_pets }}}}, function(e, docs) {
      res.json(docs);
  });
});

此代码通过seeking_pets硬编码进行编译和工作正常 - 访问/users/0/findmatches按预期返回用户test1。我暂时从请求中的seekingPets中提取userID列表并在collection.find中搜索它。这两条评论线是我尝试过没有成功的。我还尝试将collection转换为array

1 个答案:

答案 0 :(得分:1)

由于find是异步方法,因此必须实现回调才能获取从数据库返回的值。另请注意,您的硬编码值是字符串,但seekPets数组是对象。

试试这个:

router.get('/:id/findmatches', function(req, res) {
  var db = req.db;
  var collection = db.get('users');
  var uid = req.params.id;

  collection.findOne({ userID: uid }, function(err, user)
      var seeking_pets = [].
      for (var i = 0; i < user.seekingPets.length; i++) {
        seeking_pets.push(user.seekingPets[i].type);
      }

      collection.find({ petsForSale: { $elemMatch: { type: { $in: seeking_pets }}}}, function(e, docs) {
          res.json(docs);
      });

  });
});

请注意,我使用findOne来获取对象而不是数组,并从此对象获取seekPets数组。当然,您可以改进此代码,消除一些可分配的变量,如seeking_pets,并在未找到ID时处理数据库错误。