Populate one path of an object nested inside array for specific fileds - mongodb

My Posts Schema has a "comments" array path, for each "comment", "user" is objectId to User Modal. How could I populate only "name", "_id", "thumbnailURI" for the user.
what the posts db looks like:
[
...
{
"_id": "5ce5b41222fa4937f8a495e5",
"owner": "5ce5b41123456789f8a495e5",
"uri": "uri.jpg",
"comments": [
{
"date": "2019-05-23T23:24:47.554Z",
"_id": "5ce72bbf88781b35fca696ce",
"user": "5cdda3a4f5a8a077a9352f38",
"content": "cute!!!"
},
{
"date": "2019-05-23T23:28:52.941Z",
"_id": "5ce72cb46fba6f1bece267db",
"user": "5cdda3a4f5a8a077a9352f38",
"content": "cute!!!"
}
],
"createAt": "2019-05-22T20:41:54.290Z",
"__v": 0
},
...
]
I want the "comments" looks like this:
"comments": [
{
"date": "2019-05-23T23:24:47.554Z",
"_id": "5ce72bbf88781b35fca696ce",
"user": {
"name": "name",
"_id": "5ce72cb46fb5ce72cb46fb"
"thumbnailURI": "thumbnailURI.jpg"
},
"content": "cute!!!"
},
{
"date": "2019-05-23T23:28:52.941Z",
"_id": "5ce72cb46fba6f1bece267db",
"user": {
"name": "name",
"_id": "5ce72cb46fb5ce72cb46fb"
"thumbnailURI": "thumbnailURI.jpg"
},
"content": "cute!!!"
}
],
Tried
posts
.getByOwners(owners)
.populate('owner', 'username thumbnail _id')
.populate({
path: "comments",
populate: {
path: "user",
model: "user",
}
});
get empty "comments" array
Thank you!

Thanks for the advises.
I have a "user" model with some paths
There is no "comments" model. "comments" is an array embedded in "post" model.
The query looks like this:
posts
.findById(id)
.populate('owner', 'username thumbnail _id')
.populate("comments.user", 'username thumbnail _id')
This is the final result I want:
"comments": [
{
"date": "2019-05-23T23:24:47.554Z",
"_id": "5ce72bbf88781b35fca696ce",
"user": {
"thumbnail": "pic1.jpg",
"_id": "5cdda3a4f5a8a077a9352f38",
"username": "a"
},
"content": "cute!!!"
},
{
"date": "2019-05-23T23:28:52.941Z",
"_id": "5ce72cb46fba6f1bece267db",
"user": {
"thumbnail": "pic2.jpg",
"_id": "5cdda3a4f5a8a077a9352f38",
"username": "a"
},
"content": "cute!!!"
}
],

Related

Enrich array of objects with another document based on a condition

Given two collections users and activities, I want to enrich users.friends.user with all relevant activities, such that users.friends.user matches doc2.invitations.userId.
Below describes exactly what I would like:
user f24b189f-9e00-4d2b-b7f2-148a265fae7c is not a part of any activity, so their activities array is [].
user 223f2e04-6f0c-40a3-a88a-69d0127f2e92 is a part of an activity, so their activities array is populated with the activity object.
Raw:
db={
"users": [
{
"_id": "9c69a57f-e90a-43be-b559-449e973c6cba",
"__v": {
"$numberInt": "0"
},
"friends": [
{
"status": "ACCEPTED",
"user": "f24b189f-9e00-4d2b-b7f2-148a265fae7c"
},
{
"status": "ACCEPTED",
"user": "223f2e04-6f0c-40a3-a88a-69d0127f2e92"
}
]
}
],
"activities": [
{
"_id": {
"$oid": "63a92531bc6dea668f93bb06"
},
"invitations": [
{
"_id": {
"$oid": "63a92531bc6dea668f93bb07"
},
"userId": "9c69a57f-e90a-43be-b559-449e973c6cba",
"status": "ACCEPTED"
},
{
"_id": {
"$oid": "63a92544bc6dea668f93bb09"
},
"userId": "223f2e04-6f0c-40a3-a88a-69d0127f2e92",
"status": "ACCEPTED"
},
],
"__v": {
"$numberInt": "0"
}
}
]
}
Expected result:
"expectedResult": [
{
"_id": "9c69a57f-e90a-43be-b559-449e973c6cba",
"__v": {
"$numberInt": "0"
},
"friends": [
{
"status": "ACCEPTED",
"activities": [{
"_id": {
"$oid": "63a92531bc6dea668f93bb06"
},
"invitations": [
{
"_id": {
"$oid": "63a92531bc6dea668f93bb07"
},
"userId": "9c69a57f-e90a-43be-b559-449e973c6cba",
"status": "ACCEPTED"
},
{
"_id": {
"$oid": "63a92544bc6dea668f93bb09"
},
"userId": "223f2e04-6f0c-40a3-a88a-69d0127f2e92",
"status": "ACCEPTED"
},
],
"__v": {
"$numberInt": "0"
}
}]
},
{
"status": "ACCEPTED",
"activities": []
}
]
}
]
And here's a link to the playground.
I played around with aggregate and populate, but this use case is unlike a regular "join", which is throwing me off. Any pointers will be appreciated.

MongoDB lookup with multiple nested levels

In my application, I have a section of comments and replies under some documents.
Here's how my database schema looks like
db.updates.insertOne({
"_id": "62347813d28412ffd82b551d",
"documentID": "17987e64-f848-40f3-817e-98adfd9f4ecd",
"stream": [
{
"id": "623478134c449b218b68f636",
"type": "comment",
"text": "Hey #john, we got a problem",
"authorID": "843df3dbbdfc62ba2d902326",
"taggedUsers": [
"623209d2ab26cfdbbd3fd348"
],
"replies": [
{
"id": "623478284c449b218b68f637",
"type": "reply",
"text": "Not sure, let's involve #jim here",
"authorID": "623209d2ab26cfdbbd3fd348",
"taggedUsers": [
"26cfdbbd3fd349623209d2ab"
]
}
]
}
]
})
db.users.insertMany([
{
"_id": "843df3dbbdfc62ba2d902326",
"name": "Manager"
},
{
"_id": "623209d2ab26cfdbbd3fd348",
"name": "John"
},
{
"_id": "26cfdbbd3fd349623209d2ab",
"name": "Jim"
},
])
I want to join those two collections, and replace user ids with complete user information on all levels. So the final JSON should look like this
{
"_id": "62347813d28412ffd82b551d",
"documentID": "17987e64-f848-40f3-817e-98adfd9f4ecd",
"stream": [
{
"id": "623478134c449b218b68f636",
"type": "comment",
"text": "Hey #john, we got a problem",
"author": {
"_id": "843df3dbbdfc62ba2d902326",
"name": "Manager"
},
"taggedUsers": [
{
"_id": "623209d2ab26cfdbbd3fd348",
"name": "John"
}
],
"replies": [
{
"id": "623478284c449b218b68f637",
"type": "reply",
"text": "Not sure, let's involve #jim here",
"author": {
"_id": "623209d2ab26cfdbbd3fd348",
"name": "John"
},
"taggedUsers": [
{
"_id": "26cfdbbd3fd349623209d2ab",
"name": "Jim"
}
]
}
]
}
]
}
I know how to do the $lookup on the top-level fields, including pipelines, but how can I do with the nested ones?

finding document based on different input mongodb

let bondNumber1 = "100000000001"
let bondNumber2 = "00000001"
let bondNumber3 = "000001"
let bondNumber4 = "0001"
I need to choose the user whose contain these bondNumber in their data and I want them separately, like the user contain bondNumber1 value retreived separately and the user who contain bondNumber2 value retreived seperatly and so on.
[{
"_id": {
"$oid": "601af5cadea1ae126ac56bab"
},
"status": "pending",
"bondNumber": "100000000001",
"date": {
"$date": "1970-01-19T15:52:59.587Z"
},
"type": "sold"
},{
"_id": {
"$oid": "601af80fdea1ae126ac56bac"
},
"status": "pending",
"bondNumber": "100000000002",
"date": {
"$date": "1970-01-19T15:53:00.172Z"
},
"type": "sold"
},{
"_id": {
"$oid": "601afc0be3abcd1b474c546a"
},
"status": "pending",
"bondNumber": "100000000003",
"date": {
"$date": "1970-01-19T15:53:01.192Z"
},
"type": "sold"
},{
"_id": {
"$oid": "601afe7ce3abcd1b474c546b"
},
"status": "pending",
"bondNumber": "100000000004",
"date": {
"$date": "1970-01-19T15:53:01.816Z"
},
"type": "active"
}]
Try this one:
let inputBondNumbers = ["100000000001","00000001","000001","0001"]
let users = await db.collectionNameHere.find({
bondNumber: {$in : inputBondNumbers}
})

Nested lookup in mongodb

{
"_id": "445454",
"students": ["7894556", "5454454"]
}
This is my actual data. After first lookup I got a result like:
{
"_id": "445454",
"students": [{
"name": "Jose",
"parent": "45566622"
},{
"name": "Mathew",
"parent": "7889665"
}]
}
but actual answer I required is something like this
{
"_id": "445454",
"students": [{
"name": "Jose",
"parent": {
"_id": "45566622",
"name": "Cristy"
}
}, {
"name": "Mathew",
"parent": {
"_id": "7889665",
"name": "Abraham"
}
}]
}
somebody please help me. I not expert in mongodb.

Mongo Aggs and total count

I experiencing some trouble in mongodb to do a query on collection to get all documents filtered, paginate(with skip and limit) and get the total count like that
The chat document look like that:
{
"_id": "c603db3e75ec76f5a4dff559bc525e29",
"members": [{
"user": "5b2b0d5135cfd60185034bf6",
"status": "creator"
}, {
"user": "5b31dc3f88284a009fa847e5",
"status": "member"
}],
"messages": [{
"_id": 2,
"from": "5b2b0d5135cfd60185034bf6",
"parse_mode": "none",
"text": "fffasdfsa",
"attachment": null,
"time": 1529995684119,
"type": "text"
},
{...},
{...}
]}
And i would like to get result like that
{
total_count: 3,
chats: [{
"_id": "c603db3e75ec76f5a4dff559bc525e29",
"members": [{
"user": "5b2b0d5135cfd60185034bf6",
"status": "creator"
}, {
"user": "5b31dc3f88284a009fa847e5",
"status": "member"
}],
"creator": {
"user": "5b2b0d5135cfd60185034bf6",
"status": "creator"
},
"lastMessage": {
"_id": 4,
"from": "5b2b0d5135cfd60185034bf6",
"parse_mode": "none",
"text": "aasdas",
"attachment": null,
"time": 1529995698736,
"type": "text"
},
"messages": [{
"_id": 2,
"from": "5b2b0d5135cfd60185034bf6",
"parse_mode": "none",
"text": "fffasdfsa",
"attachment": null,
"time": 1529995684119,
"type": "text"
}, {
"_id": 3,
"from": "5b2b0d5135cfd60185034bf6",
"parse_mode": "none",
"text": "weqw",
"attachment": null,
"time": 1529995690015,
"type": "text"
}, {
"_id": 4,
"from": "5b2b0d5135cfd60185034bf6",
"parse_mode": "none",
"text": "aasdas",
"attachment": null,
"time": 1529995698736,
"type": "text"
}]
},
{...},
{...}
]
}
My query is
collection<DbChat>('chats').aggregate([
{
$match: {
messages: { $exists: true }
}
},
{ $unwind: '$messages' },
{ $unwind: '$members' },
{ $group: {_id: '$_id', members: { $push: '$members' }, member: { $last: '$members' }, creator: { $first: '$members' }, messages: {$push: '$messages' } , lastMessage: {$last: '$messages'}}},
{ $sort: this.sort},
]}.skip(skip).limit(size)
with this query i dont get the total_count I tried lot of things but i didnt found a way to get the result and the count in the same query.
Thanks