intermediate
Schema design
Выбирайте embedding или referencing по read locality, write contention, document growth и consistency boundaries.
Проектирование схемы MongoDB — выбор между embedding связанных данных в один документ и referencing по идентификатору. Решение следует за read locality, write contention, ростом документа и границами consistency — а не за рефлексами SQL-нормализации.
// Embed: снимок товара в заказе — один read на checkout
{ orderId: 1, items: [{ productId: 9, title: "Mug", price: 12 }] }
// Reference: автор у многих постов — обновление профиля без перезаписи постов
{ postId: 1, authorId: "u_42", title: "..." }
// отдельная коллекция users; fetch или $lookup по необходимости
| Предпочитать embedding | Предпочитать referencing | |------------------------|--------------------------| | One-to-few, читаются вместе | One-to-many с неограниченным ростом | | Данные принадлежат родительскому aggregate | Общая сущность обновляется отдельно | | Допустима snapshot-семантика | Нужна сильная consistency между aggregates | | Ограниченный размер массива | Отдельные индексы на тип сущности |
Гибриды часты: snapshot + ссылка на live data; bucket time series по дням; материализованные summary collections для дашбордов.
На интервью: опишите одну связь в продукте и защитите embed vs reference конкретными read/write flows.
Типовые ошибки: embedding неограниченных списков комментариев; referencing с N+1 без batching или `$lookup`; дублирование изменяемых данных; transactions вместо исправления модели.
Компромисс — простота чтения vs fan-out обновлений: embedding оптимизирует happy read path; referencing сохраняет общие сущности, но добавляет join или лишние round trips.
Чеклист:
- Классифицируйте связи как one-to-few vs one-to-many.
- Оцените рост документа и горячие поля записи.
- Сформулируйте consistency между aggregates.
- Упомяните денормализованные snapshots и срок их жизни.