Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
1.4k views
in Technique[技术] by (71.8m points)

mongodb apply sort to lookup results

If I have a user and post collection

{"_id": 1, "name": "User 1"}
{"_id": 2, "name": "User 2"}

{"_id": 1, "title": "Post 1", "userId": 1, "createdAt": ISODate("2017-07-24T04:12:54.255Z")}
{"_id": 2, "title": "Post 2", "userId": 1, "createdAt": ISODate("2017-07-25T04:12:54.255Z")}
{"_id": 3, "title": "Post 1", "userId": 2, "createdAt": ISODate("2017-07-24T04:12:54.255Z")}

How can I list all users with their latest post? Would be something like

{
  "_id": 1,
  "name": "User 1",
  "post": {
    "_id": 2,
    "title": "Post 2",
    "userId": 1,
    "createdAt": ISODate("2017-07-25T04:12:54.255Z")
  }
}

I know I can easily use $lookup, $unwind post, then $sort by post.createdAt, but that leave me with redundant user (User 1 will be listed twice for Post 1 and Post 2).

I don't know how can I use $group to remove duplicates while keep maintaining other fields (name, post.title, etc)

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

I solved the duplicates using $group and $first

db.getCollection('user').aggregate([
    {$lookup: {from: "post", localField: "_id", foreignField: "userId", as: "post"}},
    {$unwind: { path: "$post", preserveNullAndEmptyArrays: true }},
    {$sort: {"post.createdAt": -1}},
    {$group: {"_id": "$_id", "name": {$first: "$name"}, "post": {$first: "$post"}},
    {$project: {"_id": 1, "name": 1, "post": 1}}
])

Feel free to post your answer


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...