BMC IO DocsBMC IO Docs
IO v6
IO v7
Notes
Docs
IO v6
IO v7
Notes
Docs
  • IO Framework v7

    • О фреймворке
    • Что изменилось в 7 версии
    • IO7 Framework vs Laravel 13 — Сравнение
    • Структура
    • Варианты проектов
    • Доступ к участкам проекта
    • Разворачивание нового проекта
    • Установка проекта
    • Запуск локальной разработки
  • API

    • Обзор API
    • IOCore::call() и IOCore::callAction()
    • Создание API
  • CLI

    • Обзор CLI
    • iocli
    • Кастомные CLI команды
  • Работа с базами данных

    • Обзор работы с базами данных
    • Cron / Планировщик задач (Schedule)
    • Фабрики
    • Миграции
    • Сидеры
    • Query Builder
    • Подключение MinIO
    • Подключение MongoDB
    • Подключение MySQL
    • Подключение PostgreSQL
    • Подключение ProxySQL
    • Подключение RabbitMQ
    • Подключение Redis
  • Логирование

    • Обзор логирования
    • IOEvent - Логирование событий
    • Pinba (PinbaManager) - Профилировщик
  • Модели

    • Обзор моделей
    • CRUD операции
    • Связи моделей
  • Очереди

    • Обзор очередей
    • RabbitMQ
  • Маршруты

    • Обзор маршрутов
    • Определение маршрутов
    • Middleware
  • Сессии

    • Обзор сессий
    • Кроссдоменная SSO
    • JWT авторизация
    • Социальная авторизация
    • OAuth2
    • Keycloak
  • Twig

    • Обзор Twig
    • Формы (FormBuilder)
    • Twig функции
  • Тестирование

    • Обзор тестирования
    • Unit тесты
  • Backend

    • Настройки проекта Conf.php
    • Настройки модуля Module.php
    • Настройки composer
    • Функции фреймворка
    • Вспомогательные функции (Helpers)
    • Глобальные переменные
    • Константы фреймворка
    • Event класс
    • Core класс
    • Route и работа с ними
    • Request и работа с ними
    • Middleware и работа с ними
    • Class и работа с ними
    • Api model и работа с ними
    • Template и работа с ними
    • Мультиязычность и словарь фраз
    • Bin скрипты и работа с ними
    • Cron скрипты и работа с ними
    • $ioSession и работа с сессией
    • $ioHash и работа с кешем
    • $ioXCache и работа с кешем
    • $iodb и работа с базой данных
    • Миграции
  • Frontend

    • Twig шаблонизатор и работа с ним
    • Twig функции
    • Twig фильтры
    • Twig контекст
    • Настройка NPM
    • Сборка Frontend составляющей
    • Обращение к Api через JS
    • Хранилище (store)
    • Навигация в хосте
    • Навигация в микрофронтенде
    • Параметры микрофронтенда
    • Проверка полномочий
  • Tailux UI Компоненты

    • Базовый UI

      • AvatarDot
      • Avatar
      • Badge
      • Button
      • Card
      • ConfirmModal
      • Divider
      • Highlight
      • Tag
    • Загрузка

      • Circlebar
      • Progress
      • Skeleton
      • Spinner
    • Навигация

      • Accordion
      • AccordionButton
      • AccordionHeader
      • AccordionItem
      • AccordionPanel
      • AccordionProvider
      • Pagination
      • PaginationControl
      • PaginationItems
      • PaginationDots
      • PaginationFirst
      • PaginationLast
      • PaginationNext
      • PaginationPrevious
    • Отображение данных

      • Box
      • Collapse
      • ContextualHelp
      • ScrollShadow
      • Timeline
      • TimelineItem
    • Элементы таблиц

      • Table
      • CollapsibleSearch
      • ColumnFilter
      • CopyableCell
      • DateFilter
      • FacetedFilter
      • FilterSelector
      • PaginationSection
      • RadioFilter
      • RangeFilter
      • ResponsiveFilter
      • RoleFilter
      • SelectedRowsActions
      • TableColumnVisibility
      • TableSettings
      • TableSortIcon
    • Элементы форм

      • Checkbox
      • Combobox
      • DatePicker
      • Filepond
      • Input
      • Listbox
      • Radio
      • Range
      • Select
      • StyledSwitch
      • Swap
      • SwapOn
      • SwapOff
      • Switch
      • Textarea
      • TextEditor
      • Upload

Подключение MongoDB

Внимание

Данная статья документации написана нейросетью. Возможны некоторые расхождения и неточность информации!

  • Требования
  • MongoManager
    • Статические методы
    • Методы конфигурации
    • Методы подключения
    • CRUD операции
    • Агрегация
    • Транзакции
    • Безопасное выполнение
  • Примеры
    • Полная инициализация
    • Работа с документами
    • Агрегация
    • Транзакция
  • Рекомендации
  • FAQ
    • Что делать, если MongoDB недоступен?
    • Как подключиться к Replica Set?
    • Как работает ленивая загрузка?
    • Как использовать GridFS?
    • Как создать индексы?

Руководство по подключению к MongoDB в IO7 фреймворке.

Требования

Для работы с MongoDB необходим PHP расширение mongodb:

pecl install mongodb

Или через apt:

apt-get install php-mongodb

MongoManager

Пространство имён: IO\Database

Менеджер MongoDB с ленивой загрузкой соединений. Реализован как синглтон.

Статические методы

getInstance()

public static function getInstance(): self

Получить синглтон-экземпляр менеджера.

$manager = MongoManager::getInstance();

Методы конфигурации

addConfig()

public function addConfig(
    string $uri,
    string $database,
    string $name = 'default',
    array $options = []
): self

Добавить конфигурацию подключения (ленивая загрузка — подключение устанавливается при первом обращении).

ПараметрТипЗначение по умолчаниюОбязателенОписание
$uristring—ДаMongoDB URI подключения
$databasestring—ДаИмя базы данных
$namestring'default'НетИмя подключения
$optionsarray[]НетДополнительные опции подключения
$manager = MongoManager::getInstance();

$manager
    ->addConfig('mongodb://localhost:27017', 'mydb', 'main')
    ->addConfig('mongodb://replica1:27017,replica2:27017', 'logs', 'logs', [
        'replicaSet' => 'rs0',
    ]);

Методы подключения

isAvailable()

public function isAvailable(?string $name = null): bool

Проверить доступность подключения.

if (MongoManager::getInstance()->isAvailable()) {
    // MongoDB доступен
}

getClient()

public function getClient(?string $name = null): \MongoDB\Client

Получить клиент MongoDB.

ПараметрТипЗначение по умолчаниюОбязателенОписание
$name?\stringnullНетИмя подключения (null — default)

getDatabase()

public function getDatabase(?string $name = null): \MongoDB\Database

Получить объект базы данных.

getCollection()

public function getCollection(
    string $collection,
    ?string $connection = null
): \MongoDB\Collection

Получить объект коллекции.

ПараметрТипЗначение по умолчаниюОбязателенОписание
$collectionstring—ДаИмя коллекции
$connection?\stringnullНетИмя подключения
$users = MongoManager::getInstance()->getCollection('users');
$logs = MongoManager::getInstance()->getCollection('logs', 'logs');

CRUD операции

find()

public function find(
    string $collection,
    array $filter = [],
    array $options = [],
    ?string $connection = null
): array

Поиск документов.

ПараметрТипЗначение по умолчаниюОбязателенОписание
$collectionstring—ДаИмя коллекции
$filterarray[]НетКритерии фильтрации
$optionsarray[]НетОпции запроса
$connection?\stringnullНетИмя подключения
$activeUsers = MongoManager::getInstance()->find('users', [
    'active' => true,
], [
    'limit' => 10,
    'sort'  => ['created_at' => -1],
]);

findOne()

public function findOne(
    string $collection,
    array $filter = [],
    array $options = [],
    ?string $connection = null
): ?array

Найти один документ.

$user = MongoManager::getInstance()->findOne('users', [
    '_id' => new \MongoDB\BSON\ObjectId('...'),
]);

if ($user) {
    echo $user['name'];
}

insert()

public function insert(
    string $collection,
    array $document,
    ?string $connection = null
): \MongoDB\InsertOneResult

Вставить один документ.

$result = MongoManager::getInstance()->insert('users', [
    'name'   => 'Иван',
    'email'  => 'ivan@example.com',
    'active' => true,
]);

$newId = $result->getInsertedId();

insertMany()

public function insertMany(
    string $collection,
    array $documents,
    ?string $connection = null
): \MongoDB\InsertManyResult

Вставить несколько документов.

$result = MongoManager::getInstance()->insertMany('logs', [
    ['msg' => 'Событие 1', 'level' => 'info'],
    ['msg' => 'Событие 2', 'level' => 'error'],
    ['msg' => 'Событие 3', 'level' => 'warning'],
]);

echo "Вставлено: {$result->getInsertedCount()}";

update()

public function update(
    string $collection,
    array $filter,
    array $update,
    array $options = [],
    ?string $connection = null
): \MongoDB\UpdateResult

Обновить один документ.

$result = MongoManager::getInstance()->update('users', [
    '_id' => new \MongoDB\BSON\ObjectId('...'),
], [
    '$set' => ['active' => false],
]);

updateMany()

public function updateMany(
    string $collection,
    array $filter,
    array $update,
    array $options = [],
    ?string $connection = null
): \MongoDB\UpdateResult

Обновить несколько документов.

$result = MongoManager::getInstance()->updateMany('logs', [
    'created_at' => ['$lt' => new \MongoDB\BSON\UTCDateTime('-30 days')],
], [
    '$set' => ['archived' => true],
]);

delete()

public function delete(
    string $collection,
    array $filter,
    array $options = [],
    ?string $connection = null
): \MongoDB\DeleteResult

Удалить один документ.

deleteMany()

public function deleteMany(
    string $collection,
    array $filter,
    array $options = [],
    ?string $connection = null
): \MongoDB\DeleteResult

Удалить несколько документов.

$result = MongoManager::getInstance()->deleteMany('temp_data', [
    'expires_at' => ['$lt' => new \MongoDB\BSON\UTCDateTime()],
]);

Агрегация

aggregate()

public function aggregate(
    string $collection,
    array $pipeline,
    ?string $connection = null
): array

Выполнить агрегационный pipeline.

ПараметрТипЗначение по умолчаниюОбязателенОписание
$collectionstring—ДаИмя коллекции
$pipelinearray—ДаАгрегационный pipeline
$connection?\stringnullНетИмя подключения
// Подсчёт по статусу
$results = MongoManager::getInstance()->aggregate('orders', [
    ['$group' => [
        '_id'   => '$status',
        'count' => ['$sum' => 1],
        'total' => ['$sum' => '$amount'],
    ]],
    ['$sort' => ['count' => -1]],
]);

Транзакции

startSession()

public function startSession(): \MongoDB\ClientSession

Начать сессию (для транзакций).

transaction()

public function transaction(callable $callback, ?string $connection = null)

Выполнить транзакцию.

$result = MongoManager::getInstance()->transaction(function (\MongoDB\ClientSession $session): bool {
    // Все операции в рамках транзакции
    $session->getDatabase()->selectCollection('accounts')->updateOne(
        ['_id' => 'user1'],
        ['$inc' => ['balance' => -100]],
        ['session' => $session]
    );

    $session->getDatabase()->selectCollection('accounts')->updateOne(
        ['_id' => 'user2'],
        ['$inc' => ['balance' => 100]],
        ['session' => $session]
    );

    return true;
});

Безопасное выполнение

whenAvailable()

public function whenAvailable(
    callable $callback,
    $default = null,
    ?string $connection = null
)

Выполнить функцию только если MongoDB доступен.

$user = MongoManager::getInstance()->whenAvailable(function(MongoManager $manager): ?array {
    return $manager->findOne('users', ['_id' => $id]);
}, null);

if ($user === null) {
    // MongoDB недоступен или пользователь не найден
}

Примеры

Полная инициализация

use IO\Database\MongoManager;

$mongo = MongoManager::getInstance();

$mongo
    ->addConfig('mongodb://localhost:27017', 'myapp', 'main')
    ->addConfig('mongodb://localhost:27017', 'myapp_logs', 'logs');

// Проверка доступности
if ($mongo->isAvailable()) {
    echo "MongoDB подключён\n";
}

Работа с документами

$users = MongoManager::getInstance()->getCollection('users');

// Вставка
$result = $users->insertOne([
    'name'  => 'Иван',
    'email' => 'ivan@example.com',
    'tags'  => ['admin', 'vip'],
    'meta'  => [
        'created_ip' => '192.168.1.1',
        'browser'    => 'Chrome',
    ],
]);

// Поиск
$user = $users->findOne(['_id' => $result->getInsertedId()]);

// Обновление
$users->updateOne(
    ['_id' => $result->getInsertedId()],
    ['$push' => ['tags' => 'premium']]
);

// Удаление
$users->deleteOne(['_id' => $result->getInsertedId()]);

Агрегация

// Статистика по пользователям
$stats = MongoManager::getInstance()->aggregate('orders', [
    // Группировка по статусу
    ['$group' => [
        '_id'          => '$status',
        'count'        => ['$sum' => 1],
        'total_amount' => ['$sum' => '$amount'],
        'avg_amount'   => ['$avg' => '$amount'],
    ]],
    // Сортировка по количеству
    ['$sort' => ['count' => -1]],
    // Лимит
    ['$limit' => 10],
]);

foreach ($stats as $stat) {
    echo "Статус: {$stat['_id']}\n";
    echo "  Количество: {$stat['count']}\n";
    echo "  Сумма: {$stat['total_amount']}\n";
}

Транзакция

$result = MongoManager::getInstance()->transaction(function (\MongoDB\ClientSession $session): bool {
    $db = $session->getDatabase('myapp');

    // Списание
    $db->selectCollection('accounts')->updateOne(
        ['_id' => 'user1'],
        ['$inc' => ['balance' => -500]],
        ['session' => $session]
    );

    // Зачисление
    $db->selectCollection('accounts')->updateOne(
        ['_id' => 'user2'],
        ['$inc' => ['balance' => 500]],
        ['session' => $session]
    );

    // Логирование
    $db->selectCollection('transfers')->insertOne([
        'from'   => 'user1',
        'to'     => 'user2',
        'amount' => 500,
    ], ['session' => $session]);

    return true;
});

Рекомендации

  1. Используйте whenAvailable() для отказоустойчивости — MongoDB не должен блокировать приложение
  2. Настройте replica set для продакшен-окружения
  3. Используйте индексы для ускорения запросов
  4. Избегайте $unset — используйте $set с null
  5. Используйте транзакции для критических операций
  6. Разделяйте коллекции для данных и логов

FAQ

Что делать, если MongoDB недоступен?

$mongo = MongoManager::getInstance();

if ($mongo->isAvailable()) {
    $data = $mongo->find('logs', ['level' => 'error']);
} else {
    // Fallback: читаем из файлов или другой БД
    $data = [];
}

Как подключиться к Replica Set?

$mongo->addConfig(
    'mongodb://replica1:27017,replica2:27017,replica3:27017',
    'mydb',
    'main',
    ['replicaSet' => 'rs0']
);

Как работает ленивая загрузка?

Подключение устанавливается только при первом обращении к getDatabase(), getCollection(), find() и т.д. Конфигурация через addConfig() не создает соединения.

Как использовать GridFS?

$bucket = MongoManager::getInstance()->getDatabase()->selectGridFSBucket();

// Загрузка
$bucket->uploadFromStream('file.txt', fopen('/path/to/file.txt', 'r'));

// Скачивание
$download = $bucket->openDownloadStreamByName('file.txt');
stream_copy_to_stream($download, fopen('/tmp/downloaded.txt', 'w'));

Как создать индексы?

$collection = MongoManager::getInstance()->getCollection('users');

$collection->createIndex(['email' => 1], ['unique' => true]);
$collection->createIndex(['status' => 1, 'created_at' => -1]);
Prev
Подключение MinIO
Next
Подключение MySQL