MongoDB's document model gives you incredible flexibility — but without discipline, that flexibility becomes a liability. These are the patterns I reach for when designing schemas for production Node.js applications.
Embed vs Reference
Embed when data is accessed together, has a 1-to-few relationship, and the embedded document belongs to one parent. Reference when data is shared across documents, has 1-to-many with unbounded growth, or needs to be queried independently. The rule of thumb: model data the way your application uses it, not the way SQL taught you.
Indexing Strategy
Every query that touches more than a few thousand documents needs an index. Use compound indexes (field A + field B) when you always query both together. Put the equality field first, then the range field, then the sort field — this is the ESR rule and it keeps indexes efficient.
Mongoose Best Practices
Validate at the schema level with built-in validators, not just in your route handlers. Use lean() for read-heavy endpoints — it skips Mongoose document hydration and returns plain objects, significantly improving throughput. Define timestamps: true to get createdAt and updatedAt automatically.