Skip to content

Резервное копирование

Три слоя данных, которые нужно сохранять:

СлойГде живётЧем бэкапить
База данныхvolume Postgrespg_dump (+ встроенный tenant:backup)
Файлы (вложения)volume SeaweedFSкопия каталога данных / s3-синхронизация
Конфигурацияenv-файл, traefik/*, composeкопия файлов (секреты!)

Поисковый индекс Meilisearch бэкапить не нужно — он полностью восстанавливается командой search:rebuild.

База данных

Полный дамп (основной механизм)

bash
docker exec orbita_onpremise_db pg_dump -U orbita orbita > backup_$(date +%Y%m%d_%H%M).sql

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

  • снимать ежедневно по cron хост-системы + обязательно перед каждым обновлением;
  • сжимать (| gzip) и уносить с сервера (s3/объектное хранилище/другой хост) — бэкап на том же диске не переживёт отказ диска;
  • хранить минимум 14 суточных копий и несколько недельных.

Пример cron на хосте:

bash
# /etc/cron.d/orbita-backup
30 2 * * * root docker exec orbita_onpremise_db pg_dump -U orbita orbita | gzip > /backup/orbita_$(date +\%Y\%m\%d).sql.gz && find /backup -name 'orbita_*.sql.gz' -mtime +14 -delete

Встроенный бэкап тенантов

Приложение само делает логические бэкапы данных тенантов — планировщик запускает tenant:backup ежедневно в 03:00:

  • формат — SQL-файл из INSERT ... ON CONFLICT DO NOTHING (переносим между стендами, см. перенос тенанта);
  • складывается в backups/tenants/<tenant_id>/ на диске из filesystems.backups_disk — задаётся переменной BACKUPS_DISK в .env (по умолчанию local — это storage внутри backend-контейнера, дампы не переживают его пересоздание; рекомендуется BACKUPS_DISK=s3, тогда дампы лежат в SeaweedFS и попадают в бэкап файлов);
  • хранятся последние 30 копий на тенанта, старые удаляются автоматически;
  • ручной запуск: php artisan tenant:backup --tenant=<ID>.

Восстановление дампа тенанта — командой tenant:restore (не сырым psql: на SaaS-схеме дамп требует переписывания имён динамических таблиц, команда делает это сама):

bash
php artisan tenant:restore latest --from-disk --tenant=<ID> --wipe   # свежайший дамп, со сносом текущих данных
php artisan tenant:restore /path/to/tenant_5_20260726_030000.sql     # из файла, merge-режим
php artisan search:rebuild                                           # после восстановления

Без --wipe действует merge-семантика: существующие строки не изменяются, созданные после снятия дампа — не удаляются. Восстановление возможно только в тот же tenant_id. Данные pivot-таблиц связей входят в дамп начиная с формата v3 (при --wipe pivot пересоздаются из дампа); дампы старого формата v2 восстанавливаются без затрагивания pivot-таблиц. Дамп формата v3 требует актуальной версии tenant:restore — старая сборка его отклонит.

Это дополнение к pg_dump, а не замена: тенант-бэкап не содержит платформенных таблиц (пользователи других тенантов, настройки, лицензия).

Файлы (SeaweedFS)

bash
# Простой способ — копия каталога данных контейнера
docker cp orbita_onpremise_s3:/data ./backup_files_$(date +%Y%m%d)

Для регулярного бэкапа удобнее монтировать volume и синхронизировать его rsync-ом/restic-ом на внешнее хранилище. Файлы иммутабельны (вложения не перезаписываются), поэтому инкрементальные бэкапы дёшевы.

Конфигурация

Сохраните вне сервера (в менеджере секретов):

  • env-файл стенда (onpremise.env / prod.env) — особенно APP_KEY: без него зашифрованные данные из дампа БД не расшифровать;
  • traefik/ (включая acme/acme.json, иначе после восстановления сертификаты будут выпускаться заново);
  • локальные правки compose-файлов, если они есть.

Восстановление

Порядок на чистом сервере:

  1. Развернуть стенд по инструкции с тем же env-файлом (тот же APP_KEY!), но не выполнять инициализацию данных (сиды/tenant:init).
  2. Остановить всё, кроме БД: docker compose ... stop backend queue queue-reports scheduler reverb frontend.
  3. Залить дамп:
    bash
    cat backup.sql | docker exec -i orbita_onpremise_db psql -U orbita -d orbita
  4. Восстановить файлы в volume SeaweedFS (обратный docker cp / rsync).
  5. Поднять остальные сервисы, затем:
    bash
    docker exec orbita_onpremise_backend php artisan optimize:clear
    docker exec orbita_onpremise_backend php artisan search:rebuild
  6. Проверить: логин, открытие записей, скачивание старого вложения, поиск.

Репетиция восстановления

Бэкап, который ни разу не восстанавливали, — это гипотеза, а не бэкап. Прогоните восстановление на тестовой VM хотя бы раз в квартал.

Orbita ITSM — документация для системных администраторов