MongoDB版本3.4.10 (应用程序正在使用Meteor框架)
目标:在运行时根据需要将_id引用的文档聚合到包含的文档中。
我有Materials
,Models
和Catalog
集合,其中包含以下文档:
材料
{ "_id" : "cf4KgXw7ZK6ukdzR7", "name" : "parquet_wood_mahogany" }
模型
{
"_id" : "Mwp5eYYZ4GZzvZuoK",
"name" : "top_square_chamfered",
"type" : "top"
}
{
"_id" : "CqhS2m2RcLZ2Bm4eb",
"name" : "skirt_square",
"type" : "skirt"
}
{
"_id" : "dYP22ajALnWBwpBj2",
"name" : "leg_square",
"type" : "leg"
}
目录
{
"_id" : "EcRGzPAq79giYKrbY",
...,
"specs" : {
...,
"models" : [
{
"mesh" : "Mwp5eYYZ4GZzvZuoK",
"material" : "cf4KgXw7ZK6ukdzR7"
},
{
"mesh" : "CqhS2m2RcLZ2Bm4eb",
"material" : "cf4KgXw7ZK6ukdzR7"
},
{
"mesh" : "dYP22ajALnWBwpBj2",
"material" : "cf4KgXw7ZK6ukdzR7"
}
]
}
}
所需汇总后返回的文档格式:
{
"_id" : "EcRGzPAq79giYKrbY",
...,
"specs" : {
"dimensions" : {
...,
},
"models" : [
{
"mesh" : {
"_id" : "Mwp5eYYZ4GZzvZuoK",
"name" : "top_square_chamfered",
"type" : "top"
},
"material" : {
"_id" : "cf4KgXw7ZK6ukdzR7",
"name" : "parquet_wood_mahogany"
}
},
{
"mesh" : {
"_id" : "CqhS2m2RcLZ2Bm4eb",
"name" : "skirt_square",
"type" : "skirt"
},
"material" : {
"_id" : "cf4KgXw7ZK6ukdzR7",
"name" : "parquet_wood_mahogany"
}
},
{
"mesh" : {
"_id" : "dYP22ajALnWBwpBj2",
"name" : "leg_square",
"type" : "leg"
},
"material" : {
"_id" : "cf4KgXw7ZK6ukdzR7",
"name" : "parquet_wood_mahogany"
}
}
]
}
}
我没有包含任何查询代码,因为它与实际情况相去甚远,以至于成为噪音。我一直在尝试将aggregate
与$lookup
组合使用,但是我没有找到跟我想要的相近的东西。 MongoDB v3.6 pipeline
语法将使此操作变得更加容易...但是在v3.4中我完全不知所措。
如果可能的话,我想避免使用多个数据库请求来组合此信息。任何建议的帮助将不胜感激!
编辑:有效的解决方案-
db.catalog.aggregate([
{ "$lookup": {
"from": 'models',
"localField": "specs.models.mesh",
"foreignField": "_id",
"as": "models.mesh"
}},
{ "$lookup": {
"from": 'materials',
"localField": "specs.models.material",
"foreignField": "_id",
"as": "models.material"
}},
{ "$unwind": "$models.mesh" },
{ "$unwind": "$models.material" },
{ "$group":{
"_id": "$_id",
"title": { "$first": "$title" },
"desc": { "$first": "$desc" },
"thumbnail": { "$first": "$thumbnail" },
"createdBy": { "$first": "$createdBy" },
"createdAt": { "$first": "$createdAt" },
"specs": { "$first": "$specs" },
"models": { "$push": "$models" }
}},
{ "$project": {
"_id": "$_id",
"title": "$title",
"desc": "$desc",
"thumbnail": "$thumbnail",
"createdBy": "$createdBy",
"createdAt": "$createdAt",
"specs.dimensions": "$specs.dimensions",
"specs.models": "$models",
}}
])
答案 0 :(得分:2)
您可以尝试以下汇总
db.catalog.aggregate([
{ "$lookup": {
"from": 'models',
"localField": "specs.models.mesh",
"foreignField": "_id",
"as": "models.mesh"
}},
{ "$lookup": {
"from": 'materials',
"localField": "specs.models.material",
"foreignField": "_id",
"as": "models.material"
}},
{ "$unwind": "$models.mesh" },
{ "$unwind": "$models.material" },
{ "$group":{
"_id": "$_id",
"title": { "$first": "$title" },
"desc": { "$first": "$desc" },
"thumbnail": { "$first": "$thumbnail" },
"createdBy": { "$first": "$createdBy" },
"createdAt": { "$first": "$createdAt" },
"specs": { "$first": "$specs" },
"models": { "$push": "$models" }
}},
{ "$project": {
"title": "$title",
"desc": "$desc",
"thumbnail": "$thumbnail",
"createdBy": "$createdBy",
"createdAt": "$createdAt",
"specs.dimensions": "$specs.dimensions",
"specs.models": "$models",
}}
])