java - Group by query in a nested document -


document structure:

collection: mycollection

{     "_id" : objectid("578818ba8872933f6452c5b5"),     "user" : objectid("578818ba8872933f6452c5b5") ,     "entries" : {         "items" : [              {                 "_id" : objectid("578819018872933f6452c5ba")                 "date" : isodate("2016-07-14t22:57:58.715z"),                 "values" : [                      { "type" : a, "value" : 4 },                      { "type" : b, "value" : 3 },                           ...                 ]             },              ...         ]     } } 

expected result

  • group date (day wise, ignore time part)
  • average value each type

    {     "_id" : "2016-07-14",    "values" : [                 { "type" : "a", "avgvalue" : 3.2 },                 { "type" : "b", "avgvalue" : 4.2 },                 ...               ] } 

tried did not help

db.getcollection('mycollection').aggregate(     [         {             "$match" : {                          "user" : objectid("578818ba8872933f6452c5b5") ,                         "entries.items.date" : {"$gte" : new isodate("2016-07-11t00:00:00.715z"),"$lt" : new isodate("2016-07-18t00:00:00.715z")}                      }         },         { "$unwind" : "entires.items"},         { "$unwind" : "$entries.items.values"},         {             "$group" :  { "_id" : { '$year' : '$entries.items.date','$month' : '$entries.items.date','$day' : '$entries.items.date' },                            "values" :   [{ "type": "$entries.items.values.type",                                            "avgvalue" : { "$avg" : "$entries.items.values.value"}                                           }                                        ]                         }         }     ] ) 

what correct way of achieving result?

you can make 2 groups, 1 calculating average per type & date, pushing type & average value array , group these date :

in aggregate.js :

var ret = db.device.aggregate(     [{         "$match": {             "user": objectid("578818ba8872933f6452c5b5"),             "entries.items.date": {                 "$gte": new isodate("2016-07-11t00:00:00.715z"),                 "$lt": new isodate("2016-07-18t00:00:00.715z")             }         }     }, {         "$unwind": "$entries.items"     }, {         "$unwind": "$entries.items.values"     }, {         $project: {             user: 1,             entries: 1,             day: {                 year: {                     $year: "$entries.items.date"                 },                 month: {                     $month: "$entries.items.date"                 },                 day: {                     $dayofmonth: "$entries.items.date"                 }             }         }     }, {         $project: {             user: 1,             entries: 1,             day: {                 $concat: [{                         $substr: ["$day.year", 0, 4]                     },                     "-", {                         $substr: ["$day.month", 0, 2]                     },                     "-", {                         $substr: ["$day.day", 0, 2]                     }                 ]             }         }     }, {         $group: {             "_id": {                 "date": "$day",                 "type": "$entries.items.values.type"             },             "avgvalue": {                 "$avg": "$entries.items.values.value"             }         }     }, {         $group: {             "_id": "$_id.date",             "values": {                 "$push": {                     "type": "$_id.type",                     "avgvalue": "$avgvalue"                 }             }         }     }] ).toarray();  printjson(ret); 

test :

mongo --quiet 127.0.0.1/yourdb aggregate.js 

i used two projections before grouping because didn't grouping _id working on system :

'$year' : '$entries.items.date','$month' : '$entries.items.date','$day' : '$entries.items.date' 

i dont know if comes mongo version 2.6

result gives :

[     {         "_id" : "2016-7-14",         "values" : [             {                 "type" : "b",                 "avgvalue" : 4.5             },             {                 "type" : "a",                 "avgvalue" : 6             }         ]     } ] 

Comments

Popular posts from this blog

javascript - Slick Slider width recalculation -

jsf - PrimeFaces Datatable - What is f:facet actually doing? -

angular2 services - Angular 2 RC 4 Http post not firing -