MongoDB
MongoDB — документоориентированная NoSQL-СУБД, хранящая записи в виде JSON-подобных документов без обязательной единой схемы.
Что такое MongoDB
MongoDB (монго, mongo db) — документоориентированная NoSQL-СУБД. Вместо строк в таблицах со строгой схемой она хранит документы — JSON-подобные объекты, каждый со своим набором полей. Название от английского humongous (огромный).
Ключевая идея: объект приложения кладётся в базу как есть, целиком, без разбора на пять связанных таблиц и обратной сборки через JOIN.
// Документ в коллекции users
{
_id: ObjectId("65a1f2e3c4d5b6a7f8091234"),
email: "ivan@example.com",
profile: { name: "Иван", city: "Москва" }, // вложенный объект
tags: ["pro", "beta"], // массив прямо в поле
lastLogin: ISODate("2026-07-01T10:00:00Z")
}
Соседний документ той же коллекции может иметь другой набор полей — база это допускает.
Терминология
| Реляционная БД | MongoDB |
|---|---|
| Таблица | Коллекция (collection) |
| Строка | Документ (document) |
| Колонка | Поле (field) |
JOIN |
Вложенность или $lookup |
| Первичный ключ | _id |
Физически документы хранятся в BSON — бинарном формате, который расширяет JSON типами ObjectId, Date, Decimal128 и бинарными данными. Поле _id создаётся автоматически, если не задано явно.
Базовые операции
db.users.insertOne({ email: "a@b.com", tags: ["new"] })
db.users.find({ "profile.city": "Москва" }) // поиск по вложенному полю
db.users.find({ tags: "pro" }) // поиск по элементу массива
db.users.find({ age: { $gte: 18, $lt: 65 } })
db.users.updateOne(
{ email: "a@b.com" },
{ $set: { "profile.city": "Казань" }, $push: { tags: "vip" } }
)
db.users.createIndex({ email: 1 }, { unique: true }) // уникальный индекс
db.users.find({ email: "a@b.com" }).explain("executionStats")
Aggregation pipeline
Аналитические запросы строятся конвейером стадий, каждая обрабатывает выход предыдущей:
db.orders.aggregate([
{ $match: { createdAt: { $gte: ISODate("2026-01-01") } } }, // фильтр
{ $group: { _id: "$city", revenue: { $sum: "$total" } } }, // группировка
{ $sort: { revenue: -1 } },
{ $limit: 10 }
])
$match ставят первой стадией не для красоты: он отсекает документы до тяжёлых операций и умеет пользоваться индексами, тогда как после $group индекса уже нет.
Схема данных: вложить или сослаться
Главное решение при проектировании — и главный источник проблем:
- Вложить (embed) — подходит, когда данные читаются вместе с родителем, не растут бесконечно и не нужны отдельно. Комментарии в посте, адрес в профиле, позиции в заказе.
- Сослаться (reference) — когда сущность самостоятельна, переиспользуется или коллекция растёт неограниченно. Пользователь и его заказы.
Ограничение, о которое спотыкаются: документ не может превышать 16 МБ. Массив, который растёт без предела (лента событий, лог), рано или поздно упрётся в лимит — такие данные выносят в отдельную коллекцию.
Соединение через $lookup существует, но это не полноценный JOIN: он медленнее, ограничен по возможностям, и строить на нём модель как в реляционной базе — верный способ получить худшее от обоих миров.
Транзакции и надёжность
Операции над одним документом атомарны всегда. Многодокументные ACID-транзакции появились в версии 4.0 и работают на replica set:
const session = db.getMongo().startSession()
session.startTransaction()
try {
// операции над несколькими коллекциями
session.commitTransaction()
} catch (e) {
session.abortTransaction()
}
Они есть, но платны по производительности. Если приложению постоянно нужны транзакции через несколько коллекций — это сигнал, что данные реляционные и им место в PostgreSQL.
Ещё одна ручка надёжности — writeConcern: { w: 1 } подтверждает запись после primary, { w: "majority" } — после большинства узлов. Второе медленнее, но переживает падение primary без потери подтверждённых записей.
Масштабирование
- Replica set — набор из primary и secondary-узлов с автоматическим выбором нового primary при отказе. Базовая конфигурация для продакшена: три узла, потому что для кворума нужно нечётное число. Репликация здесь же даёт чтение с secondary.
- Sharded cluster — шардирование по ключу через процессы
mongosи конфигурационные серверы. Выбор shard key необратим по сути и определяет, будет ли нагрузка размазана или соберётся на одном шарде.
Лицензия и когда выбирать
С 2018 года MongoDB распространяется под SSPL — лицензией, которая не признана Open Source Initiative и ограничивает предоставление MongoDB как сервиса. Для собственной эксплуатации это не помеха; для встраивания в продукт условия стоит читать внимательно. Есть форк FerretDB, реализующий протокол MongoDB поверх PostgreSQL.
Mongo уместен, когда структура документов действительно разнородна и меняется, объект читается целиком по своему ключу, а горизонтальный рост важнее связей. Если данные табличные и связанные — реляционная база останется проще и надёжнее, тем более что jsonb в PostgreSQL закрывает потребность в документах без второй СУБД.
Связанные термины
- Реляционные и NoSQL БД — где документные базы среди остальных
- СУБД — класс, к которому относится MongoDB
- PostgreSQL — альтернатива с типом
jsonb - Шардирование — sharded cluster и выбор shard key
- Репликация — replica set и failover
- Индексы в БД — без них
findидёт полным сканом
Готовы запустить GPU-задачу?
Запустить GPU-сервер