removing uncessary keys in result mongoose - mongodb

I am currently getting a response in mongoose like this
{
"_id" : "5a0be40836341c8ef9dc6d9d",
"Username" : "Adkins Daugherty",
"ContactDetail" : {
"ApiID" : "5a0be408ed6983954888bdb5",
"ContactName" : "Pace Roach",
}
}
But i want like this :
{
"_id" : "5a0be40836341c8ef9dc6d9d",
"Username" : "Adkins Daugherty",
"ApiID" : "5a0be408ed6983954888bdb5",
"ContactName" : "Pace Roach",
}
How can i do this using mongoose. My collection name is contacts
Thanks
EDIT-1
db.contacts.aggregate([{
$match: { Username: 'year_Adkins Daugherty' } },
{ "$unwind": "$ContactDetail" },
{
"$group": { "_id": "$_id",
"ApiID": "$ContactDetail.ApiID"
}
}
])

I think I got an answer in $project
return Contact.aggregate(
[
{ $match: { Username: regex } },
{
$project:{
Username:1,
ApiID:"$ContactDetail.ApiID",
Name:"$ContactDetail.ContactName",
ProfileImageUrl:"$ContactDetail.ProfileImageUrl",
OutletName:"$ContactDetail.OutletName"
}
}
]
).exec()
The result I got is
{
"_id": "5a0be40836341c8ef9dc6d9d",
"Username": "year_Adkins Daugherty",
"ApiID": "5a0be408ed6983954888bdb5",
"Name": "Pace Roach",
"ProfileImageUrl": "http://placehold.it/256x256",
"OutletName": "Codehow___kjvolyi3ye"
}

Related

Query nested array from document

Given the following document data in collection called 'blah'...
[
{
"_id" : ObjectId("60913f55987438922d5f0db6"),
"procedureCode" : "code1",
"description" : "Description 1",
"coding" : [
{
"system" : "ABC",
"code" : "L111"
},
{
"system" : "DEFG",
"code" : "S222"
}
]
},
{
"_id" : ObjectId("60913f55987438922d5f0dbc"),
"procedureCode" : "code2",
"description" : "Description 2",
"coding" : [
{
"system" : "ABC",
"code" : "L999"
},
{
"system" : "DEFG",
"code" : "X3333"
}
]
}
]
What I want to get is all of the coding elements where system is ABC for all parents, and an array of codes like so.
[
{ "code": "L111" },
{ "code": "L999" },
]
If I use db.getCollection('blah').find({"coding.system": "ABC"}) I get the parent document with any child in the coding array of ICD.
If I use...
db.getCollection("blah")
.find({ "coding.system": "ABC" })
.projection({ "coding.code": 1 })
I do get the parent documents which have a child with a system of "ABC", but the coding for "DEFG" seems to come along for the ride too.
{
"_id" : ObjectId("60913f55987438922d5f0db6"),
"coding" : [
{
"code" : "L989"
},
{
"code" : "S102"
}
]
},
{
"_id" : ObjectId("60913f55987438922d5f0dbc"),
"coding" : [
{
"code" : "L989"
},
{
"code" : "X382"
}
]
}
I have also tried experimenting with:
db.getCollection("blah").aggregate(
{ $unwind: "$coding" },
{ $match: { "system": "ICD" } }
);
.. as per this page: mongoDB query to find the document in nested array
... but go no where fast with that approach. i.e. no records at all.
What query do I need, please, to achieve something like this..?
[
{ "code": "L111" },
{ "code": "L999" },
...
]
or even better, this..?
[
"L111",
"L999",
...
]
db.collection.aggregate([
{
$match: { "coding.system": "ABC" }
},
{
$unwind: "$coding"
},
{
$match: { "coding.system": "ABC" }
},
{
$project: { code: "$coding.code" }
}
])
mongoplayground
db.collection.aggregate([
{
$match: { "coding.system": "ABC" }
},
{
$unwind: "$coding"
},
{
$match: { "coding.system": "ABC" }
},
{
$group: {
_id: null,
coding: { $push: "$coding.code" }
}
}
])
mongoplayground
Instead of $unwind, $match you can also use $filter:
db.collection.aggregate([
{ $match: { "coding.system": "ABC" } },
{
$project: {
coding: {
$filter: {
input: "$coding",
cond: { $eq: [ "$$this.system", "ABC" ] }
}
}
}
}
])

How to update array of objects to LowerCase in mongodb?

I need to update the role in team array to lowercase.
db.users.find().pretty().limit(1)
{
"_id" : ObjectId("5d9fd81d3d598088d2ea5dc9"),
"employed" : "USA-Atlanta",
"firstName" : "Rory",
"siteRole" : "super admin",
"status" : "active",
"team" : [
{
"name" : "SALES AND MARKETING",
"displayName" : "S&M",
"role" : "Manager"
}
]
}
Tried this code.I m getting it with normal fields.
db.users.find( {}, { 'role': 1 } ).forEach(function(doc) {
db.users.update(
{ _id: doc._id},
{ $set : { 'role' : doc.role.toLowerCase() } },
{ multi: true }
)
});
sample output
"team" : [
{
"name" : "SALES AND MARKETING",
"displayName" : "S&M",
"role" : "manager"
}
]
I think the below Aggregation query is what you are looking for
var count = 0;
db.users.aggregate([
{
"$match": {
"team.role": {$exists: true}
}
},
{
"$project": {
"_id": 1,
// "team": 1,
"teamModified": {
"$map": {
"input": "$team",
"as": "arrayElems",
"in": {
"$mergeObjects": [
"$$arrayElems",
{"role": {"$toLower": "$$arrayElems.role"}}
]
}
}
}
}
},
]).forEach(function(it) {
db.users.updateOne({
"_id": it["_id"]
}, {
"$set": {
"team": it["teamModified"]
}
})
printjson(++count);
})
printjson("DONE!!!")
Note: I haven't tested the script properly in my local, so do let me know if it didn't help you out

Mongo DB - To get the last data for every unique email address - Grouped by Regions

db.TYPE_Join_STEP_COUNTER_GPS.aggregate([
{ $match: { 'Time.ObservationTimestamp': { $gte: ISODate("2019-01-01T00:00:00+00:00"), $lt: ISODate("2019-02-02T00:00:00+00:00") } } },
{
$group: {
_id: { users: "$userAccount.userEmail" },
sensorValue: { $addToSet: "$sensorValue.sensorValue" }
}
},
{
$unwind: "$sensorValue"
},
{
$group: { _id: "$_id", lastdata: {$last: "$sensorValue"} }
}
])
I got the below output for this query.
/* 1 */
{
"_id" : {
"users" : "test1#gmail.com"
},
"lastdata" : "245"
},
/* 2 */
{
"_id" : {
"users" : "test2#gmail.com"
},
"lastdata" : "135"
}
What I need - I need the last data of Sensor value for unique email ids in every region. I tried to add one more group by condition with respect to region but it didnt work. Please let me know if I am missing something. Thank you in advance.
Sample Collection:
{
"_id" : ObjectId("5c52f5370ad3076c2398ba83"),
"userAccount" : {
"userId" : "115867679428105538091",
"userEmail" : "test1#gmail.com"
},
"deviceId" : "9312dfc5b63063c7",
"sensorType" : "TYPE_Join_STEP_COUNTER_GPS",
"sensorValue" : {
"sensorValue" : "257",
"regoin" : "Region1"
},
"Time" : {
"ObservationTimestamp" : ISODate("2019-01-30T00:00:00.000+00:00")
}
}
Expected Output:
/* 1 */
{
"_id" : {
"regoin" : "Region1"
},
users: "Test1#gmail.com" , "lastdata" : "135"
users: "Test2#gmail.com" , "lastdata" : "105"
},
/* 2 */
{
"_id" : {
"regoin" : "Region2"
},
users: "Test1#gmail.com" , "lastdata" : "105"
users: "Test2#gmail.com" , "lastdata" : "100"
},
You can use $last accumulator to get the last sensor value
db.TYPE_Join_STEP_COUNTER_GPS.aggregate([
{ "$match": {
"Time.ObservationTimestamp": {
"$gte": ISODate("2019-01-01T00:00:00+00:00"),
"$lt": ISODate("2019-02-02T00:00:00+00:00")
}
}},
{ "$group": {
"_id": { "userEmail": "$userAccount.userEmail", "regoin": "$sensorValue.regoin" },
"sensorValue": { "$last": "$sensorValue.sensorValue" }
}},
{ "$group": {
"_id": "$_id.regoin",
"data": {
"$push": {
"user": "$_id.userEmail",
"sensorValue": "$sensorValue"
}
}
}}
])

How to get nested 3 label array object in Mongo Query?

Basically the structure is :
{
"_id" : ObjectId("123123"),
"stores" : [
{
"messages" : [
{
"updated_time" : "2018-05-15T05:12:25+0000",
"message_count" : 4,
"thread_id" : "123",
"messages" : [
{
"message" : "Hi User ",
"created_time" : "2018-05-15T05:12:25+0000",
"message_id" : "111",
},
{
"message" : "This is tes",
"created_time" : "2018-05-15T05:12:21+0000",
"message_id" : "222",
}
]
},
],
"store_id" : "123"
}
]
}
I have these values to get message_id object : 111. So how to get this object, any idea or help will be appreciated. THanks
store_id: 123,
thread_id:123,
message_id:111
The simplest way would be to $unwind all the nested arrays and then use $match to get single document. You can also add $replaceRoot to get only nested document. Try:
db.collection.aggregate([
{ $unwind: "$stores" },
{ $unwind: "$stores.messages" },
{ $unwind: "$stores.messages.messages" },
{ $match: { "stores.store_id": "123", "stores.messages.thread_id": "123", "stores.messages.messages.message_id": "111" } },
{ $replaceRoot: { newRoot: "$stores.messages.messages" } }
])
Prints:
{
"created_time": "2018-05-15T05:12:25+0000",
"message": "Hi User ",
"message_id": "111"
}
To improve the performance you can use $match after every $unwind to filter out unnecessary data as soon as possible, try:
db.collection.aggregate([
{ $unwind: "$stores" },
{ $match: { "stores.store_id": "123" } },
{ $unwind: "$stores.messages" },
{ $match: { "stores.messages.thread_id": "123" } },
{ $unwind: "$stores.messages.messages" },
{ $match: { "stores.messages.messages.message_id": "111" } },
{ $replaceRoot: { newRoot: "$stores.messages.messages" } }
])

How to check keys of key value pair inside mongodb structure

I have a mongodb collection where objects are structured as such:
{
"id": "1234",
"history": [
{
"userid": 100,
"myobjects": [{id, id1, id4}]
},
{
"userid": 200,
"myobjects": [{id2, id3, id5}]
},
}
Goal: if my userid is 100, return an object that doesn't contain my userid in its history. I'm guessing it'd be some kind of "my userid not in keys of history field" but i'm not sure how to write that out. Here's my basic idea:
Collection.findOne(
{
in_progress : null,
history : {"$nin": myuserid } ???
}
);
Any help would be appreciated!
Use MongoDB aggregation.
db.test.aggregate([
{
"$unwind" : "$history"
},
{
"$match" : {
"history.userid" : {
"$ne" : 100
}
}
},
{
"$group" : {
"_id" : "$id",
"history" : {
"$push" : "$history"
}
}
}
]);