带有$lookup的MongoDB聚合只包括(或项目)从查询返回的一些字段

带有$lookup的MongoDB聚合只包括(或项目)从查询返回的一些字段,mongodb,aggregation-framework,lookup,Mongodb,Aggregation Framework,Lookup,在mongo中,在使用$lookup进行聚合之后,我希望请求只返回一些字段,而不是整个文档 我有以下疑问: db.somecollection.aggregate([{ $lookup: { from: "campaigns", localField: "campId", foreignField: "_id", as: "campaign" } }, { $unwind: "$campaign" }, {

在mongo中,在使用
$lookup
进行
聚合之后,我希望请求只返回一些字段,而不是整个文档

我有以下疑问:

db.somecollection.aggregate([{
    $lookup: {
        from: "campaigns",
        localField: "campId",
        foreignField: "_id",
        as: "campaign"
    }
}, {
    $unwind: "$campaign"
}, {
    $lookup: {
        from: "entities",
        localField: "campaign.clientid",
        foreignField: "_id",
        as: "campaign.client"
    }
}]);
此请求将返回以下内容:

{
"_id" : ObjectId("56cc7cd1cc2cf62803ebfdc7"),
"campId" : ObjectId("56c740e4479f46e402efda84"),
"articleId" : ObjectId("56c742c06094640103ba3843"),
"campaign" : {
    "_id" : ObjectId("56c740e4479f46e402efda84"),
    "clientid" : ObjectId("56c740b8479f46e402efda83"),
    "client" : [
        {
            "_id" : ObjectId("56c740b8479f46e402efda83"),
            "username" : "someusername",
            "shhh" : "somehashedpassword",
            "email" : "mail@mail.com",
        }
    ]
}

请求运行良好,但我想筛选
活动.client
中的字段,以便仅获取例如
\u id
用户名
。在MongoDB
聚合请求中是否有这样做的方法?

为了帮助其他人,@SiddhartAjmera给出了正确的答案,我只需要为嵌套值添加双引号,如“campaign.clientid”

最终代码应为:

db.somecollection.aggregate([
      {
        "$lookup": {
          "from": "campaigns",
          "localField": "campId",
          "foreignField": "_id",
          "as": "campaign"
        }
      },
      {
        "$unwind": "$campaign"
      },
      {
        "$lookup": {
          "from": "entities",
          "localField": "campaign.clientid",
          "foreignField": "_id",
          "as": "campaign.client"
        }
      },
      {
        "$project": {
          "_id": 1,
          "campId": 1,
          "articleId": 1,
          "campaign._id": 1,
          "campaign.clientid": 1,
          "campaign.client._id": 1,
          "campaign.client.username": 1
        }
      }
]);

只需在前面的答案中添加一点:您可以将0添加到要忽略的项目项中,其余的将被检索,因此您不需要使用1来编写所有列表:

db.somecollection.aggregate([
  {
    "$lookup": {
      "from": "campaigns",
      "localField": "campId",
      "foreignField": "_id",
      "as": "campaign"
    }
  },
  {
    "$unwind": "$campaign"
  },
  {
    "$lookup": {
      "from": "entities",
      "localField": "campaign.clientid",
      "foreignField": "_id",
      "as": "campaign.client"
    }
  },
  {
    "$project": {
      "campaign.client.shhh": 0
    }
  }
])

$lookup

db.somecollection.aggregate([{
    $lookup: {
        from: "campaigns",
        localField: "campId",
        foreignField: "_id",
        as: "campaign"
    }
}, {
    $unwind: "$campaign"
}, {
    $lookup: {
        from: "entities",
        let: { client_id: "$campaign.clientid" },    
        pipeline : [
            { $match: { $expr: { $eq: [ "$_id", "$$client_id" ] } }, },
            { $project : { _id:1, username:1 } }
        ],
        as: "campaign.client"
    }
}]);

我知道现在回答这个问题已经很晚了。但在我看来,更新有时是非常有益的。
项目阶段很好,但您仍然会在
$lookup
阶段请求整个dock。字段仅在其后面的投影阶段中过滤。

MongoDB 3.6发布后,现在可以向
$lookup
阶段添加管道,以指定多个连接条件。在他们的官方文档中查找更多详细信息。


您可以按如下方式转换聚合管道,以获得所需的结果:

db.somecollection.aggregate([{
    $lookup: {
        from: "campaigns",
        localField: "campId",
        foreignField: "_id",
        as: "campaign"
    }
}, {
    $unwind: "$campaign"
}, {
    $lookup: {
        from: "entities",
        let: {clientid: '$campaign.clientid'},
        pipeline: [
           { '$match': 
             { '$expr': 
               { 
                  '$eq': ['$_id', '$$clientid']   
               }
             }
           },
           { '$project': 
              '_id': 1,
              'username': 1
           }
        ]
        as: "campaign.client"
    }
}]);
这样,您就可以在
$lookup
阶段内过滤加入集合的字段。

请注意内部管道的
$match
阶段内的
$
符号。它用于表示在
let
块中定义的自定义字段。

使用
$project
阶段<代码>{$project:{{u id:1,campId:1,articleId:1,活动。{u id:1,campaign.clientid:1,campaign.client.{u id:1,campaign.client.username:1}}
@SiddharthAjmera你应该把它转换成一个答案,你刚刚救了我的一天!为什么我们要添加$unwind?为什么需要它?@Faisal它会以数组的形式返回活动,如果你不做$unwind…有没有办法只从父项返回所有内容(在项目中),从子项返回特定字段。(我用“*”作为指示符)例如:$project:{“*”:1,“campaign.\u id”:1,“campaign.clientid”:1,“campaign.client.\u id”:1,“campaign.client.username”:1}@mliscetrus你找到方法了吗?@mliscetrus AlpeshVasani你找到方法了吗?