Home > OS >  MongoDB nested group aggregation with 2 fields
MongoDB nested group aggregation with 2 fields

Time:07-20

I have collection call entries like this in mongoDB

[
   {
      "date": "Mon Jul 07 2022 17:15:19",
      "name": "Banana",
      "calories": 100,
      "mealID": "62d55d4de4c92d6de31e22ad",
      "type": "Lunch"
    },
    {
      "date": "Mon Jul 07 2022 17:15:19",
      "name": "Buger",
      "calories": 300,
      "mealID": "62d55d4de4c92d6de31e22ad",
      "type": "Lunch"
     },
     {
      "date": "Mon Jul 07 2022 17:15:19",
      "name": "Coffee",
      "calories": 120,
      "mealID": "62d55d4de4c92d6de31e22",
      "type": "Break fast"
     },
     {
      "date": "Mon Jul 07 2022 17:15:19",
       "name": "Omlet",
       "calories": 70,
       "mealID": "62d55d4de4c92d6de31e22ad",
       "type": "Dinner"
      },

    ]

Im trying to aggregate this with group by date and entry type (Lunch/Brake fast/Dinner) and $sum the calories per day.

[
   { _id: "Mon Jul 07 2022 17:15:19",
     entriesForTheDay: {
        "Dinner": {
        entries: [
          {name: "Omlet", calories: 70},
        ],
        count: 1,
      },
     "Break fast": {
        entries: [
          {name: "Coffee", calories: 120},
        ],
        count: 1,
      },
     "Lunch": {
        entries: [
          {name: "Banana", calories: 100},
          {name: "Buger", calories: 300},
        ],
        count: 2,
      }
     },
    totalCaloriesForThDay: 590
   }
]

I have tried with this but I'm mot sure ho to group with $type field.

[
 {$group: {_id: '$date',
                   entries: {
                        $push: {
                            entry: {
                                name: '$name',
                                calories: '$calories',
                                type: '$type'
                            },
                           }
                        },
                        count: {
                            "$sum": 1
                        }
                    }
                },
]

CodePudding user response:

Query

  • group by date and type, to push the entries
  • group by date, to count the total calories for that date

*its common way to group, if you want group by field1,field2 and also group by field2, you can start for the group with the many, and then the more general

*output is almost the same, but without data in fields, in can be exactly as you want, but saving data on fields is not good idea in general

Playmongo

aggregate(
[{"$group": 
   {"_id": {"date": "$date", "type": "$type"},
    "entries": {"$push": {"name": "$name", "calories": "$calories"}}}},
 {"$group": 
   {"_id": "$_id.date",
    "entriesForTheDay": 
     {"$push": 
       {"type": "$_id.type",
        "entries": "$entries",
        "count": {"$size": "$entries"}}},
    "totalCaloriesForThDay": {"$sum": {"$sum": "$entries.calories"}}}}])
  • Related