Group By
This stage represents the $group
stage in MongoDB.
Method Signature
public groupBy(
GroupByPipeline: GenericObject,
groupByData?: GenericObject,
): this;
public groupBy(groupBy_id: string | null): this;
public groupBy(groupBy_id: string | null, groupByData: GenericObject): this;
A quick brief about the groupBy pipeline
The groupBy pipeline is a pipeline that contains the _id
field and the fields that you want to group by, this allows you to group your data with certain fields and also return computed fields such as total documents, average, sum, etc.
Example
Let's say we have a collection of users and we want to group them by their age and return the total number of users in each group.
const users = await aggregate
.groupBy("age", {
total: $agg.count(),
})
.get();
This will return an array of objects with output like this:
[
{
"_id": 20,
"total": 2
},
{
"_id": 21,
"total": 1
},
{
"_id": 22,
"total": 1
}
]
The previous example we passed the first argument with the column name that we will group with, the second argument is optionally to gather more data about the group.
This is usually the most common use case for the groupBy pipeline.
Always head back to the groupBy pipeline to see all the available operators.
Group by multiple fields
Sometimes we need to group by multiple fields, in this case we can pass the first argument as an object, let's say we need to group all products by category and brand.
const products = await aggregate
.groupBy(
{
category: "$category",
brand: "$brand",
},
{
total: $agg.count(),
category: $agg.last("category"),
brand: $agg.last("brand"),
}
)
.get();
You may also pass the first argument as an array of strings, if the fields are not nested and you don't need to rename them.
const products = await aggregate
.groupBy(["category", "brand"], {
total: $agg.count(),
})
.get();
This is an exact match for the previous snippet.
Group By Using An object
Alternatively, you may pass an object directly to the group by method, this is the native syntax of MongoDB group pipeline.
const products = await aggregate
.groupBy({
_id: {
category: "$category",
brand: "$brand",
},
total: $agg.count(),
})
.get();
Group by year
This method will group documents by year, this is useful if you want to group documents by year and return the total number of documents in each year.
const products = await aggregate
.groupByYear("createdAt", {
total: $agg.count(),
})
.get();
Group by month
If we want to group only by months, we can use groupByMonth
method.
const products = await aggregate
.groupByMonth("createdAt", {
total: $agg.count(),
})
.get();
Group by year and month
This method will group documents by year and month, this is useful if you want to group documents by year and month and return the total number of documents in each year and month.
const products = await aggregate
.groupByYearMonth("createdAt", {
total: $agg.count(),
})
.get();
Group by date
We can group by by year/month/day using groupByDate
method.
const products = await aggregate
.groupByDate("createdAt", {
total: $agg.count(),
})
.get();
Group By day of month
This method will group documents by day of month, this is useful if you want to group documents by day of month and return the total number of documents in each day of month.
const products = await aggregate
.groupByDayOfMonth("createdAt", {
total: $agg.count(),
})
.get();
So what is the difference between groupByDate
and groupByDayOfMonth
?
groupByDate
will group documents by year/month/day, while groupByDayOfMonth
will group documents by day of month only.
Group by accepts any valid Mongodb syntax for grouping, the main objective of this method is to make it easier to group documents by adding an additional layer over the builtin MongoDB group pipeline not to replace it.