0

I have a collection which looks like this

var StoreSchema = new Schema({
name: String,
category: [String],
subCategory: [String],
});

Sample data looks like this:

[
 {
 'name':'Store1',
 'category':['Cat1','Cat2','Cat3'],
 'subCategory':['SubCat1','SubCat2']
 },
 {
 'name':'Store2',
 'category':['Cat2','Cat3','Cat4'],
 'subCategory':['SubCat1','SubCat2']
 },
 {
 'name':'Store3',
 'category':['Cat4','Cat3','Cat1'],
 'subCategory':['SubCat1','SubCat2']
 }
]

I want to get the stores grouped by their categories, I want to retrieve the store names and ids as well.

I tried using this code:

Store.aggregate([
        {$unwind: '$category'},
        {$group: { _id: '$category', count: {$sum: 1}}},
        {$project: {'_id':1, category: '$_id',count: '$count'}}
        ]);

The output I get is like this:

[
 {
  "count": 2,
  "Category": "cat1"
 },
 {
  "count": 2,
  "category": "cat2"
 }
]

Is it possible to get the all fields of stores collection as well . Something like this:

[
 {
  "stores": [{'name':'store1','id':'1'},{'name':'store3','id':'3'}],
  "count": 2,
  "Category": "cat1"
 },
 {
  "stores": [{'name':'store1','id':'1'},{'name':'store2','id':'2'}],
  "count": 2,
  "category": "cat2"
 }
]
Puneet
  • 654
  • 1
  • 8
  • 16

1 Answers1

1

You can try below aggregation. Use $push operator to add store.

Store.aggregate([
    {$unwind: '$category'},
    {$group: { _id: '$category', count: {$sum: 1}, stores:{$push:{name:'$name', id:'$id'}}}},
    {$project: {_id:0, category: '$_id',count: 1, stores:1}}
]);
s7vr
  • 73,656
  • 11
  • 106
  • 127
  • Thanks for the code. It works. Is there a way I could set the limit on the stores array. Ex: If I have 20 stores in cat1, could I set it to retrieve only 5. Can i also set a limit on all the retrieved documents? – Puneet Feb 18 '17 at 07:13
  • You are welcome. Take a look here http://stackoverflow.com/q/42258325/2683814 for slicing stores array. You can use $limit stage for limiting the retrieved documents. – s7vr Feb 18 '17 at 11:04