【问题标题】:Mongoose Query: Find an element inside an arrayMongoose 查询:在数组中查找元素
【发布时间】:2014-05-21 09:58:53
【问题描述】:

这里是Mongoose/Mongo noob:

我的数据

这是我的简化数据,每个用户都有自己的文档

{ "__v" : 1,
  "_id" : ObjectId( "53440e94c02b3cae81eb0065" ),
  "email" : "test@test.com",
  "firstName" : "testFirstName",
  "inventories" : [ 
    { "_id" : "active",
      "tags" : [ 
        "inventory", 
        "active", 
        "vehicles" ],
      "title" : "activeInventory",
      "vehicles" : [ 
        { "_id" : ObjectId( "53440e94c02b3cae81eb0069" ),
          "tags" : [ 
            "vehicle" ],
          "details" : [ 
            { "_id" : ObjectId( "53440e94c02b3cae81eb0066" ),
              "year" : 2007,
              "transmission" : "Manual",
              "price" : 1000,
              "model" : "Firecar",
              "mileageReading" : 50000,
              "make" : "Bentley",
              "interiorColor" : "blue",
              "history" : "CarProof",
              "exteriorColor" : "blue",
              "driveTrain" : "SWD",
              "description" : "test vehicle",
              "cylinders" : 4,
              "mileageType" : "kms" } ] } ] }, 
    { "title" : "soldInventory",
      "_id" : "sold",
      "vehicles" : [],
      "tags" : [ 
        "inventory", 
        "sold", 
        "vehicles" ] }, 
    { "title" : "deletedInventory",
      "_id" : "deleted",
      "vehicles" : [],
      "tags" : [ 
        "inventory", 
        "sold", 
        "vehicles" ] } ] }

如您所见,每个用户都有一个 inventories 属性,该属性是一个包含 3 个库存(activeInventory、soldInventory 和 deletedInventory)的数组

我的查询

给定用户的电子邮件和车辆 ID,我希望我的查询通过查找用户的 activeInventory 并仅返回与 ID 匹配的车辆。这是我目前所拥有的:

user = api.mongodb.userModel;
ObjectId = require('mongoose').Types.ObjectId;
return user
    .findOne({email : params.username})
    .select('inventories')
    .find({'title': 'activeInventory'})
    //also tried
    //.where('title')
    //.equals('activeInventory')
    .exec(function(err, result){
        console.log(err);
        console.log(result);
    });

这样,结果就会作为一个空数组出现。我也尝试过.find('inventories.title': 'activeInventory'),它奇怪地返回了整个库存数组。如果可能的话,我想保留链接查询格式,因为我发现它更具可读性。

我的理想查询

return user
    .findOne({email : params.username})
    .select('inventories')
    .where('title')
    .equals('activeInventory')
    .select('vehicles')
    .id(vehicleID)
    .exec(cb)

显然它不起作用,但它可以让你知道我想要做什么。

【问题讨论】:

    标签: arrays node.js mongodb mongoose


    【解决方案1】:

    获取链接查询格式...我不知道如何解析它但是,您正在搜索的是投影,您应该看看http://docs.mongodb.org/manual/reference/operator/projection/

    它可能看起来像这样:

    user.findOne({email: params.username}, {'inventories.title': {$elemMatch: "activeInventory", 'invertories.vehicle.id': $elemMatch: params.vehicleId}, function(err, result) {
        console.log(err);
        console.log(result);
    })
    

    【讨论】:

      【解决方案2】:

      使用$ 位置运算符,您可以获得结果。但是,如果您在 vehicles 数组中有多个元素,所有这些元素都将在结果中返回,因为您只能在投影中使用一个位置运算符,并且您正在使用 2 个数组(一个在另一个数组中)。

      我建议您查看aggregation framework,因为您将获得更多的灵活性。这是在 shell 中运行的针对您的问题的示例查询。我不熟悉猫鼬,但我想这仍然会帮助你,你可以翻译它:

      db.collection.aggregate([
          // Get only the documents where "email" equals "test@test.com" -- REPLACE with params.username
          {"$match" : {email : "test@test.com"}}, 
          // Unwind the "inventories" array
          {"$unwind" : "$inventories"}, 
          // Get only elements where "inventories.title" equals "activeInventory"
          {"$match" : {"inventories.title":"activeInventory"}}, 
          // Unwind the "vehicles" array
          {"$unwind" : "$inventories.vehicles"}, 
          // Filter by vehicle ID -- REPLACE with vehicleID 
          {"$match" : {"inventories.vehicles._id":ObjectId("53440e94c02b3cae81eb0069")}}, 
          // Tidy up the output
          {"$project" : {_id:0, vehicle:"$inventories.vehicles"}}
      ])
      

      这是您将得到的输出:

      {
              "result" : [
                      {
                              "vehicle" : {
                                      "_id" : ObjectId("53440e94c02b3cae81eb0069"),
                                      "tags" : [
                                              "vehicle"
                                      ],
                                      "details" : [
                                              {
                                                      "_id" : ObjectId("53440e94c02b3cae81eb0066"),
                                                      "year" : 2007,
                                                      "transmission" : "Manual",
                                                      "price" : 1000,
                                                      "model" : "Firecar",
                                                      "mileageReading" : 50000,
                                                      "make" : "Bentley",
                                                      "interiorColor" : "blue",
                                                      "history" : "CarProof",
                                                      "exteriorColor" : "blue",
                                                      "driveTrain" : "SWD",
                                                      "description" : "test vehicle",
                                                      "cylinders" : 4,
                                                      "mileageType" : "kms"
                                              }
                                      ]
                              }
                      }
              ],
              "ok" : 1
      }
      

      【讨论】:

      • 我喜欢这种方法,你的方法很好
      猜你喜欢
      • 2020-07-08
      • 2019-08-09
      • 1970-01-01
      • 2017-12-05
      • 1970-01-01
      • 1970-01-01
      • 2021-02-21
      • 2020-03-14
      • 2022-01-10
      相关资源
      最近更新 更多