In short
Need 'top five dishes by revenue this week'? In MongoDB that's an aggregation pipeline: documents flow through stages, and each stage filters, groups or reshapes them.
MongoDB's framework for transforming and analyzing data through a sequence of stages (`$match`, `$group`, `$sort`) — the NoSQL equivalent of complex SQL queries.

Think of it like this
The mango sorting line
At the mandi, mangoes roll down a belt. The first station throws out unripe ones. The next groups them by size. The last counts crates per size and lines them up, biggest first. Each station does one job and passes the rest along.
Watch it happen
Top five dishes this week
1/5$match keeps only this week's paid orders. Everything else is dropped right away.
The big ideas
What you need to know
Stages run in order
Each stage takes documents in and passes documents out. The order of stages matters a lot.
Match early
Put $match first so later stages handle fewer documents and an index can help.
$group does the maths
Group by a field and compute $sum, $avg, $min or $max for each group.
$lookup joins
Pulls matching documents from another collection, a bit like a LEFT JOIN. Use it sparingly.
See it in code
Walk through the code
1db.orders.aggregate([2 { $match: { status: "paid", placedAt: { $gte: ISODate("2026-10-20") } } },3 { $unwind: "$items" },4 { $group: {5 _id: "$items.dish",6 revenue: { $sum: { $multiply: ["$items.price", "$items.qty"] } },7 orders: { $sum: 1 },8 } },9 { $sort: { revenue: -1 } },10 { $limit: 5 },11]);1/4Keep only paid orders from this week. An index on status and placedAt makes this fast.
A $ in front of a field name, like '$items.qty', means 'the value of this field'. Run this in mongosh.
Save yourself the pain
Common mistakes
Oops
Putting $match after $group.
Do this instead
Filter first. Matching early shrinks the data and lets MongoDB use indexes.
Oops
Using $lookup in every pipeline to rebuild SQL joins.
Do this instead
If you join on every read, rethink the document shape. Embed what you read together.
Your mission
Canteen report
Quick check
Why should $match usually be the first stage?
Go deeper
- 1Build a pipeline that groups documents and computes a sum or average.
- 2Chain `$match` and `$group` stages to filter before aggregating.
- 3Compare an aggregation pipeline to the equivalent SQL `GROUP BY` query.
More topics at this stop
Stuck on this topic? Ask an Insider
Get 1:1 guidance from people who've walked this exact path — on the InsideEdge app.