Q&A
What is data modeling in MongoDB?
Overview
MongoDB stores data as BSON documents in collections. There's no fixed schema, and "foreign keys" are replaced by a deliberate design choice: embed related data directly in the parent document, or store it separately and reference it by ObjectId. Each choice has trade-offs. The fundamental question is: "How does the application access this data?"
graph TD
A[MongoDB data modeling] --> B[Embedded documents]
A --> C[Referenced documents]
B --> B1["One document, one read<br/>Fast reads, atomic updates<br/>Data duplication if reused"]
C --> C1["Separate docs, join in app / $lookup<br/>Normalized, single source of truth<br/>Multiple reads required"]
style B fill:#1e1b4b,color:#fff
Embedding (Denormalized)
Store related data inside the parent document:
{
"_id": "order_001",
"customer": "Ada",
"items": [
{ "product": "Widget A", "qty": 2, "price": 9.99 },
{ "product": "Widget B", "qty": 1, "price": 24.99 }
],
"address": {
"street": "1 Tech Lane",
"city": "London"
}
}
Benefits: One query fetches everything; writes that touch only this document are atomic; no join needed.
Choose embedding when:
- Data is only ever accessed together with the parent ("one-to-few" relationship).
- The embedded sub-documents won't grow without bound (MongoDB doc limit: 16 MB).
- The sub-documents aren't shared/referenced by multiple parents.
Referencing (Normalized)
Store the related data in its own collection and link by _id:
// orders collection
{
"_id": "order_001",
"customer_id": ObjectId("64a1..."), // reference
"product_ids": [ObjectId("..."), ObjectId("...")]
}
// customers collection
{ "_id": ObjectId("64a1..."), "name": "Ada", "email": "ada@example.com" }
Benefits: Single source of truth; no data duplication; fields change in one place.
Choose referencing when:
- Sub-data is shared by many parent documents (e.g. a product referenced by many orders).
- The array of references could grow large.
- Sub-data is frequently accessed independently of the parent.
One-to-N Relationship Patterns
| Cardinality | Strategy |
|---|---|
| One-to-few (1–dozens) | Embed in array |
| One-to-many (hundreds+) | Reference from the "many" side, or in an array if bounded |
| One-to-squillions (unbounded logs, events) | Reference from the child; don't put an unbounded array in the parent |
Schema Design Anti-Patterns to Avoid
- Unbounded arrays - embedding an ever-growing list (e.g. all log entries) in one document will hit the 16 MB limit and hurt performance.
- Massive number of collections - one collection per user/entity instead of a generic collection with a discriminator field.
- Over-normalizing - splitting data that is always accessed together into separate collections just out of habit from relational databases.
- Unnecessary
$lookups - if every query joins two collections, consider embedding.
Practical Pattern: Bucket Pattern
For time-series or unbounded data, "bucket" related records:
// Instead of one document per sensor reading (millions):
{
"sensor_id": "s1",
"date": "2026-06-01",
"readings": [23.1, 23.4, 22.9 ...] // one doc per day, array of hourly readings
}
Why This Matters in Interviews
MongoDB system-design interviews always ask about data modeling. The key principles: model for query patterns (co-locate data that's read together); the embed vs reference trade-off (simplicity/speed vs normalization); specific cardinality rules (embed "few," reference large/unbounded arrays); and the most common anti-patterns (unbounded arrays, over-normalizing). Mentioning the 16 MB document limit and that $lookup is less efficient than embedding - but necessary for shared/large data - shows practical depth.
Common Pitfalls
- Modeling MongoDB like a relational DB (normalizing everything and using
$lookupeverywhere). - Creating unbounded embedded arrays that grow without limit.
- Duplicating data with no plan for keeping it consistent when the embedded data changes.
- Ignoring update patterns - embedding is great for reads but can complicate updates to shared data.
- Over-indexing without understanding that indexes occupy RAM.
References
- MongoDB Data Modeling: https://www.mongodb.com/docs/manual/core/data-modeling-introduction/
- MongoDB Schema Design Patterns: https://www.mongodb.com/blog/post/building-with-patterns-a-summary