我有一个具有以下架构的Mongo对象 .
{
"_id" : "59fffda313d02500116e83bf::5a059c67f3ff3b001105c509",
"quizzes" : [
{
"topics" : [
ObjectId("5a05a1e1fc698f00118470e2")
],
"isCorrect" : true,
"status" : 2,
"isUsed" : true,
"askBack" : false,
"isRestricted" : false,
"rejected" : false,
"createdAt" : ISODate("2017-11-10T12:56:01.273Z"),
"updatedAt" : ISODate("2017-11-10T12:56:02.808Z"),
"answerRead" : false,
"participantAnswer" : "5a054210d74fe90011d5f5e2",
"correctAnswer" : "5a054210d74fe90011d5f5e2",
"question" : ObjectId("5a054210d74fe90011d5f5e0"),
"participant" : ObjectId("59fffda313d02500116e83bf"),
"author" : ObjectId("5a059c67f3ff3b001105c509"),
"_id" : ObjectId("5a05a1e1fc698f00118470e1")
},
{
"topics" : [
ObjectId("5a054210d74fe90011d5f5e1")
],
"isCorrect" : false,
"status" : 2,
"isUsed" : true,
"askBack" : true,
"isRestricted" : false,
"rejected" : false,
"createdAt" : ISODate("2017-11-10T12:57:33.910Z"),
"updatedAt" : ISODate("2017-11-10T12:57:33.910Z"),
"answerRead" : true,
"correctAnswer" : "5a054210d74fe90011d5f5e2",
"question" : ObjectId("5a054210d74fe90011d5f5e0"),
"participant" : ObjectId("5a059c67f3ff3b001105c509"),
"author" : ObjectId("59fffda313d02500116e83bf"),
"_id" : ObjectId("5a05a23dfc698f00118470f5")
}
],
"participants" : [
ObjectId("5a059c67f3ff3b001105c509"),
ObjectId("59fffda313d02500116e83bf")
],
"__v" : 0,
"skippedQuestionIds" : []
}
“作者”和“参与者”字段是具有以下模式的另一个集合的外键引用 .
{
"_id" : ObjectId("5739bcdd4fb7d8030050bc04"),
"password" : "$2a$06$4Rmiya6Vh9aENXxKoD56UOIG3ZiGNzH.Ed5lgY8aiJ4OidQPAf6wq",
"email" : "m@m.com",
"username" : "mm",
"birthday" : ISODate("2016-05-03T18:30:00.000Z"),
"lastName" : "m",
"firstName" : "m",
"devices" : [],
"role" : "user",
"updatedAt" : ISODate("2017-08-01T13:26:43.510Z"),
"createdAt" : ISODate("2016-05-16T12:28:13.063Z"),
"lastUpdated" : ISODate("2017-08-02T07:39:02.960Z"),
"active" : false,
"points" : 0,
"topicLocked" : [
"flirty",
"dirty",
"mahesh_test"
],
"hashfriends" : [],
"blockedList" : [],
"friends" : [
{
"user" : ObjectId("586b6fd12631000004812a68"),
"_id" : ObjectId("58e60399ca9a180004072089"),
"topicExhausted" : [],
"scoreInPercentage" : 0,
"totalQuizAnswered" : 1,
"isCrew" : false,
"isFriendo" : false,
"scoreRank" : "You’re tied 1 to 1",
"score" : 1,
"lastPlayed" : ISODate("2017-04-06T09:37:48.843Z")
}
],
"meta" : {
"totalInvites" : -3,
"totalFriends" : 1
},
"isDeleted" : false,
"__v" : 3,
"androidDevices" : [],
"iosDevices" : [],
"isAgeRestrictedCategories" : [
ObjectId("571727dde30aef0300a95725")
],
"usernameAsEntered" : "mm",
"platform" : "ios",
"celebParticipants" : [],
"lastActivity" : ISODate("2017-04-06T09:30:34.054Z"),
"lastNudged" : ISODate("2016-04-25T06:46:38.267Z")
}
我需要在第一个集合上运行聚合并限制测验子文档中的对象数量,并在updatedAt时间戳上对其进行排序 .
我还想在users集合中的quizzes数组中的每个元素中填充作者和参与者 . 但是,我很难检索到我需要的字段,即只有username,firstName,lastName,_id,meta和active .
我做到了这一点 .
db.getCollection('usergames').aggregate([{$match: {_id: "5a059c56f3ff3b001105c508::5a059c67f3ff3b001105c509"}},
{$unwind: '$quizzes'},
{$lookup: {
"from":'users',
"localField":'quizzes.author',
'foreignField': '_id',
"as": 'quizzes.author'
}},
{$unwind: '$quizzes.author'},
{$sort: {'quizzes.updatedAt': -1}},
{$group: {_id: '$_id', quizzes: {$push: '$quizzes'}}},
{$project: {
_id: 1,
'quizzes': {
$slice:['$quizzes', 0, 3]
}}
}
])
但是,这是我想要的回应 .
{
"_id" : "59fffda313d02500116e83bf::5a059c67f3ff3b001105c509",
"quizzes" : [
{
"topics" : [
ObjectId("5a054210d74fe90011d5f5e1")
],
"isCorrect" : false,
"status" : 2,
"isUsed" : true,
"askBack" : true,
"isRestricted" : false,
"rejected" : false,
"createdAt" : ISODate("2017-11-10T12:57:33.910Z"),
"updatedAt" : ISODate("2017-11-10T12:57:33.910Z"),
"answerRead" : true,
"correctAnswer" : "5a054210d74fe90011d5f5e2",
"question" : ObjectId("5a054210d74fe90011d5f5e0"),
"author" :{
"_id": "59fffda313d02500116e83bf",
"username": "f2",
"lastName": "2",
"firstName": "f",
"active": false,
"meta": {
"totalInvites": 0,
"totalFriends": 1
}
},
"participant": {
"_id": "5a059c67f3ff3b001105c509",
"username": "chandan",
"lastName": "kumar",
"firstName": "chandan",
"active": false,
"meta": {
"totalInvites": 0,
"totalFriends": 16
}
"_id" : ObjectId("5a05a23dfc698f00118470f5")
}
],
"participants" : [
ObjectId("5a059c67f3ff3b001105c509"),
ObjectId("59fffda313d02500116e83bf")
],
"__v" : 0,
"skippedQuestionIds" : []
}
可以在初始投影之后完成查找,以及如何限制字段 . 任何帮助将不胜感激 . 谢谢
1 回答
我不会完全熟悉你的模式来计算整个管道,但是如果我可以概括一下:
是的,
$lookup
可以在$project
操作后完成 . 您可以在聚合中进行多个$project
操作(实际上是多个操作) .$lookup
操作之后可能会执行$project
操作以按以下方式规范化结果:由于
$lookup
返回数组中的结果,因此上面的示例使用$arrayElemAt
获取第一个元素并逐个投影所需的属性 .