Fetch Unique Document in Mongodb? - mongodb

Sample Data:
{"_id" : ObjectId("58bd10e4ff1743c527754160"),
"data" : [
{
"No" : "70",
"Type" : "82",
"Device" : "01",
"timestamp" : "2017-03-06 13:00:32"
}]
},
{"_id" : ObjectId("58bd10sdfe4ff1743csdf0754"),
"data" : [
{
"No" : "75",
"Type" : "22",
"Device" : "02",
"timestamp" : "2017-03-06 13:00:32"
}]
}
I have some document which having same timestamp,so I want to find only unique document on the basis of timestamp.
I have done distinct of timestamp but I want full document.
desired Output:
If same timestamp is there I want only One document.

You will only get one output if you run this query.
db.getCollection('tests').aggregate([{$match:{"data.timestamp":"2017-03-06 13:00:32"}},{$limit:1}])

Solution 1:
db.your_collection.aggregate([
{
$group:{
_id:"$data.timestamp",
data:{
$first:"$data"
}
}
}
])
This will give you following :
{ "_id" : [ "2017-03-06 13:00:32" ], "data" : [ { "No" : "70", "Type" : "82", "Device" : "01", "timestamp" : "2017-03-06 13:00:32" }, { "No" : "10", "Type" : "20", "Device" : "01", "timestamp" : "2018-02-04 10:00:00" } ] }
Solution 2 :
db.your_collection.aggregate([
{ $unwind : '$data'},
{ $group : {
_id : '$data.timestamp',
'No': { $first : '$data.No'},
'Type': { $first : '$data.Type'},
'Device': { $first : '$data.Device'},
'timestamp': { $first : '$data.timestamp'},
}
}
]);
This will give you following :
[
{ "_id" : "2017-03-06 13:00:32", "No" : "70", "Type" : "82", "Device" : "01", "timestamp" : "2017-03-06 13:00:32" },
{ "_id" : "2018-02-04 10:00:00", "No" : "10", "Type" : "20", "Device" : "01", "timestamp" : "2018-02-04 10:00:00" },
]

Related

Aggregation in mongo

Below is a document from my database:
{
"_id" : ObjectId("58635ac32c9592064471cf5b"),
"agency_code" : "v5global",
"client_code" : "whirlpool",
"project_code" : "whirlpool",
"date" : {
"datetime" : 1464739200000.0,
"date" : 1464739200000.0,
"datejs" : ISODate("2016-06-01T00:00:00.000+0000"),
"datetimejs" : ISODate("2016-06-01T00:00:00.000+0000"),
"month" : NumberInt(5),
"year" : NumberInt(2016),
"day" : NumberInt(1)
},
"user" : {
"promoter_id" : NumberInt(19),
"promoter_name" : "Hira Singh Pawar",
"empcode" : "519230"
},
"counter" : {
"store_id" : NumberInt(4),
"store_name" : "Maya Sales ",
"chain_type" : "BS",
"address" : "6 Filamingo Market , Hissar",
"city" : "Hissar",
"state" : "Faridabad",
"region" : "North",
"sap_code" : "N_Far_91103948_1",
"unique_tp_code" : "91103948",
"location" : "6"
},
"insertedon" : {
"date" : 1464739200000.0,
"datejs" : ISODate("2016-06-01T00:00:00.000+0000"),
"datetimejs" : ISODate("2016-06-01T00:00:00.000+0000")
},
"insertedby" : "akshay",
"manager" : {
"manager_id" : NumberInt(5943),
"manager_name" : "Sonu Singh"
},
"type" : "display",
"data" : {
"brand" : "whirlpool",
"sku" : "60",
"model_name" : "Icemagic Fresh",
"sub_cat_name" : "DC",
"cat_name" : "Refrigerator",
"value" : NumberInt(1)
},
"IsDeleted" : false
}
I want to apply aggregation where I have to group it with city, state and region and if that counter has sold refrigerator I need that details in my result e.g if a counter has sold 2 refrigerators of whirlpool company then I want that to reflect in my result.
A counter can also sell other things like washing machines etc. So if they have sold 2 washing machines I want a result with { washingMachine: 2 }.
I have tried everything and nothing seems to be working here:
db.display_mop.aggregate( // Pipeline [
// Stage 1
{ $match: { "project_code":"whirlpool" } },
// Stage 2
{
$group: {
_id: {
"userid": "$user.promoter_id",
"userName": "$user.promoter_name",
"usercode": "$user.empcode",
"storename": "$counter.store_name",
"address": "$counter.address",
"city": "$counter.city",
"state": "$counter.state",
"region": "$counter.region"
}
}
},
],
// Options
{ allowDiskUse: true }

Delete portion of Sub Document Collection in Mongodb

I am trying to delete a section of sub documents from a collections..
Tried (and many others):
db.collection.remove( {'Segments': {$gte: '20150612141038' }} )
db.collection.remove( { 'Segments.$' : {$gte: '0150612141038' }} )
db.collection.deleteMany( { 'Segments.$' : {$gte: '0150612141038' }} )
db.collection.deleteOne( { 'Segments.$' : {$eq: '0150612141038' }} )
just can't figure out what I am doing wrong...
{
"_id" : ObjectId("56e32c5147e030bc0a000035"),
"Date" : "2015-06-12",
"UnitID" : "5",
"Segments" : {
"20150612141037" : {
"Parameters" : {
"647" : "0",
"649" : "16",
"653" : "0",
"655" : "0",
"656" : "0",
"658" : "98",
"664" : "447.0486",
"666" : "442.7083",
"677" : "122.8004",
}
},
"20150612141038" : {
"Parameters" : {
"658" : "96",
"664" : "451.3889",
"666" : "447.0486",
"677" : "122.7892"
}
},
"20150612141039" : {
"Parameters" : {
"658" : "44",
"664" : "442.7083",
"677" : "122.8004",
"704" : "1"
}
},
First of all I think your queries are wrong.
If you try this query to the mongoShell:
db.bios.find({'Segments': {$gte: '20150612141038'}})
you don't have anything as output because 20150612141038 is a document and not a field. Maybe you can reshape your schema to set 20150612141038 as a field and Segments as an array of documents:
{
"_id" : ObjectId("56e32c5147e030bc0a000035"),
"Date" : "2015-06-12",
"UnitID" : "5",
"Segments" : [
{
"segmentId" : "20150612141037",
"Parameters" : {
"647" : "0",
"649" : "16",
"653" : "0",
"655" : "0",
"656" : "0",
"658" : "98",
"664" : "447.0486",
"666" : "442.7083",
"677" : "122.8004"
}
},
{
"segmentId" : "20150612141038",
"Parameters" : {
"658" : "96",
"664" : "451.3889",
"666" : "447.0486",
"677" : "122.7892"
}
},
{
"segmentId" : "20150612141039",
"Parameters" : {
"658" : "44",
"664" : "442.7083",
"677" : "122.8004",
"704" : "1"
}
}
]
}
and then you can use $pull operator to remove documents from Segments array where the field Segments.segmentId has a certain value:
db.collection.update({},
{$pull:{Segments:{"segmentId":{$eq:"20150612141039"}}}},
{ multi: true}
)

Query a collection for the latest unique object

Question: Lets say I have the following objects in a collection:
How would I return one record per "product_id" and only the one with the highest "version" number? And is this possible to do within mongoose?
{
"_id" : ObjectId("54f765564b10883c1800002a"),
"total_invoice_fob_case" : 86.70999999999999,
"status" : "Draft",
"discount" : "3.40",
"effective_date" : ISODate("2013-08-01T06:00:00.000Z"),
"version" : 2,
"controlstate" : "AB",
"controlstate_id" : ObjectId("54d510e9e3d793f581b6bb27"),
"product" : "Product A",
"product_id" : ObjectId("54f75b5e4b1088801a000627"),
"size" : "1.75LTR",
"size_id" : ObjectId("5418a3dd750b4294c2cb3a47"),
"vendor" : "BEAM SUNTORY",
"vendor_id" : ObjectId("54ef5aa74b1088781b000169"),
"product_state_code" : "123",
"net_fob_cost" : 86.70999999999999,
"change_reason" : [
"Other"
],
"submitted" : {
"submitted_date" : ISODate("2014-05-16T06:00:00.000Z")
}
},
{
"_id" : ObjectId("54f765564b10883c1800002b"),
"total_invoice_fob_case" : 86.70999999999999,
"status" : "Draft",
"discount" : "4.40",
"effective_date" : ISODate("2013-08-01T06:00:00.000Z"),
"version" : 3,
"controlstate" : "AB",
"controlstate_id" : ObjectId("54d510e9e3d793f581b6bb27"),
"product" : "Product A",
"product_id" : ObjectId("54f75b5e4b1088801a000627"),
"size" : "1.75LTR",
"size_id" : ObjectId("5418a3dd750b4294c2cb3a47"),
"vendor" : "BEAM SUNTORY",
"vendor_id" : ObjectId("54ef5aa74b1088781b000169"),
"product_state_code" : "123",
"net_fob_cost" : 86.70999999999999,
"change_reason" : [
"Other"
],
"submitted" : {
"submitted_date" : ISODate("2014-05-16T06:00:00.000Z")
}
},
{
"_id" : ObjectId("54f765564b10883c1800002c"),
"total_invoice_fob_case" : 86.70999999999999,
"status" : "Draft",
"discount" : "3.40",
"effective_date" : ISODate("2013-08-01T06:00:00.000Z"),
"version" : 2,
"controlstate" : "AB",
"controlstate_id" : ObjectId("54d510e9e3d793f581b6bb27"),
"product" : "Product B",
"product_id" : ObjectId("54f75b5e4b1088801a000628"),
"size" : "1.75LTR",
"size_id" : ObjectId("5418a3dd750b4294c2cb3a47"),
"vendor" : "BEAM SUNTORY",
"vendor_id" : ObjectId("54ef5aa74b1088781b000169"),
"product_state_code" : "123",
"net_fob_cost" : 86.70999999999999,
"change_reason" : [
"Other"
],
"submitted" : {
"submitted_date" : ISODate("2014-05-16T06:00:00.000Z")
}
}
Sounds like a job for Mongo's aggregation framework. You can extrapolate from this example how to approach the problem.
Update: To retrieve one per product_id with the highest version you would need to also use $first:
db.products.aggregate([
{$sort: {product_id: 1, version: -1}}, // sort first so that $first pulls the correct record
{$group: {
_id: {product_id: '$product_id'}, // group by the product_id
product: {$first: $$ROOT} // only return the first document per group
}}
]);
You need an aggregation pipeline that first sorts the documents in the collection by version number descending using a $sort pipeline stage, then groups the ordered documents by product_id using the $group operator. Within the grouping use the $first operator on $$ROOT to return the first document in the sorted group:
var pipeline = [
{
"$sort": { "version": -1 }
},
{
"$group": {
"_id": "$product_id",
"value": {
"$first": "$$ROOT"
}
}
},
{
"$project": {
"_id": 0,
"product_id": "$_id",
"status": "$value.status",
"version": "$value.version",
"product" : "$value.product"
}
}
];
// Mongoose aggregation
Model.aggregate(pipeline, function (err, res) {
if (err) return handleError(err);
console.log(res); //
});
Console Output:
[
{
"product_id" : ObjectId("54f75b5e4b1088801a000628"),
"status" : "Draft",
"version" : 2,
"product" : "Product B"
},
{
"product_id" : ObjectId("54f75b5e4b1088801a000627"),
"status" : "Draft",
"version" : 3,
"product" : "Product A"
}
]
-- UPDATE --
To project the full document, replace the $project pipeline with the following:
{
"$project": {
"_id": 0,
"product": "$value"
}
}
Output:
/* 1 */
{
"result" : [
{
"product" : {
"_id" : ObjectId("54f765564b10883c1800002c"),
"total_invoice_fob_case" : 86.7099999999999940,
"status" : "Draft",
"discount" : "3.40",
"effective_date" : ISODate("2013-08-01T06:00:00.000Z"),
"version" : 2,
"controlstate" : "AB",
"controlstate_id" : ObjectId("54d510e9e3d793f581b6bb27"),
"product" : "Product B",
"product_id" : ObjectId("54f75b5e4b1088801a000628"),
"size" : "1.75LTR",
"size_id" : ObjectId("5418a3dd750b4294c2cb3a47"),
"vendor" : "BEAM SUNTORY",
"vendor_id" : ObjectId("54ef5aa74b1088781b000169"),
"product_state_code" : "123",
"net_fob_cost" : 86.7099999999999940,
"change_reason" : [
"Other"
],
"submitted" : {
"submitted_date" : ISODate("2014-05-16T06:00:00.000Z")
}
}
},
{
"product" : {
"_id" : ObjectId("54f765564b10883c1800002b"),
"total_invoice_fob_case" : 86.7099999999999940,
"status" : "Draft",
"discount" : "4.40",
"effective_date" : ISODate("2013-08-01T06:00:00.000Z"),
"version" : 3,
"controlstate" : "AB",
"controlstate_id" : ObjectId("54d510e9e3d793f581b6bb27"),
"product" : "Product A",
"product_id" : ObjectId("54f75b5e4b1088801a000627"),
"size" : "1.75LTR",
"size_id" : ObjectId("5418a3dd750b4294c2cb3a47"),
"vendor" : "BEAM SUNTORY",
"vendor_id" : ObjectId("54ef5aa74b1088781b000169"),
"product_state_code" : "123",
"net_fob_cost" : 86.7099999999999940,
"change_reason" : [
"Other"
],
"submitted" : {
"submitted_date" : ISODate("2014-05-16T06:00:00.000Z")
}
}
}
],
"ok" : 1
}

MongoDB groupby query

I have colletions containing records like
{ "type" : "me", "tid" : "1" }
{ "type" : "me", "tid" : "1" }
{ "type" : "me", "tid" : "1" }
{ "type" : "you", "tid" : "1" }
{ "type" : "you", "tid" : "1" }
{ "type" : "me", "tid" : "2" }
{ "type" : "me", "tid" : "2"}
{ "type" : "you", "tid" : "2"}
{ "type" : "you", "tid" : "2" }
{ "type" : "you", "tid" : "2"}
I have want result like below
[
{"tid" : "1","me" : 3,"you": 2},
{"tid" : "2","me" : 2,"you": 3}
]
I have tried group and; aggregate queries doesn't get required result format.
below is the group query.
db.coll.group({
key: {tid : 1,type:1},
cond: { tid : { "$in" : [ "1","2"]} },
reduce: function (curr,result) {
result.total = result.total + 1
},
initial: { total : 0}
})
it result is like
[
{"tid" : "1", "type" : "me" ,"total": 3 },
{"tid" : "1","type" : "you" ,"total": 2 },
{"tid" : "2", "type" : "me" ,"total": 2 },
{"tid" : "2","type" : "you" ,"total": 3 }
]
following is aggregate query
db.coll.aggregate([
{$match : { "tid" : {"$in" : ["1","2"]}}},
{$group : { _id : {tid : "$tid",type : "$type"},total : {"$sum" : 1}}}
])
gives following result
{
"result" :
[
{"_id" : {"tid" : "1","type" : "me"},"total" : 3},
{"_id" : {"tid" : "2","type" : "me" },"total" : 2},
{"_id" : {"tid" : "2","type" : "you"},"total" : 3}
]
"ok" : 1
}
it is possible to obtain I specified result or I have to do some manipulation in my code.
Thanks
If you change your aggregation to this:
db.so.aggregate([
{ $match : { "tid" : { "$in" : ["1", "2"] } } },
{ $group : {
_id : { tid : "$tid", type : "$type" },
total : { "$sum" : 1 }
} },
{ $group : {
_id : "$_id.tid",
values: { $push: { type: "$_id.type", total: '$total' } }
} }
])
Then your output is:
{
"result" : [
{
"_id" : "1",
"values" : [
{ "type" : "you", "total" : 2 },
{ "type" : "me", "total" : 3 }
]
},
{
"_id" : "2",
"values" : [
{ "type" : "me", "total" : 2 },
{ "type" : "you", "total" : 3 }
]
}
],
"ok" : 1
}
Although that is not the same as what you want, it is going to be the closest that you can get. And in your application, you can easily pull out the values in the same was as with what you would like to get out of it.
Just keep in mind, that in general you can not promote a value (you, me) to a key — unless your key is of a limited set (3-4 items max).

How to delete multiple ids in mongodb?

{ "_id" : ObjectId("51ee3966e4b056fe8f074f48"), "userid" : "66", "clientid" : "88", "deviceid" : "22", "timestamp" : "1374214822000"}
{ "_id" : ObjectId("51ee507ae4b056fe8f074f4a"), "userid" : "66", "clientid" : "88", "deviceid" : "22", "timestamp" : "1374214822000"}
{ "_id" : ObjectId("51ee51fee4b056fe8f074f4b"), "userid" : "66", "clientid" : "88", "deviceid" : "22", "timestamp" : "1374214822000"}
How to delete multiple ids in mongodb?
By running remove once for each ID, or perhaps using in:
db.collection.remove( { _id : { $in: [
ObjectId("51ee3966e4b056fe8f074f48"),
ObjectId("51ee3966e4b056fe8f074f4a"),
ObjectId("51ee3966e4b056fe8f074f4b")
] } } );
You can accomplish this by using the command deleteMany.
const objects = [
ObjectId("51ee3966e4b056fe8f074f48"),
ObjectId("51ee3966e4b056fe8f074f4a"),
ObjectId("51ee3966e4b056fe8f074f4b")
];
db.collection.deleteMany({_id: { $in: objects}});