Резервное копирование выделенного сервера
Рабочая схема выглядит так: ежедневный инкремент файлов и дамп СУБД во внешнее хранилище, недельная полная копия и ежемесячная проверка восстановления на отдельной машине. RAID резервным копированием не является: зеркало честно повторит ошибочное удаление и работу шифровальщика на обоих дисках одновременно.
- Правило 3-2-1: три копии данных, два разных носителя, одна копия за пределами сервера.
- Копия, из которой ни разу не восстанавливались, копией не считается — проверка раз в месяц обязательна.
- База копируется дампом или снимком файловой системы, а не построчным копированием каталога данных на живой СУБД.
- Учётная запись, которой пишет сервер, не должна иметь права удалять старые копии: иначе шифровальщик сотрёт и их.
- Опция бэкапа во внешнее хранилище стоит $10 в месяц и закрывает требование «копия вне площадки».
Что копировать и как часто
| Данные | Частота | Метод | Хранение |
|---|---|---|---|
| Базы данных | Ежедневно, активные — каждый час | Дамп плюс бинарный журнал | 14 суточных, 8 недельных |
| Файлы проекта и загрузки | Ежедневно | restic или borg, инкремент | 14 суточных, 12 месячных |
| Конфигурация системы | Ежедневно | Каталог /etc целиком | 30 суток |
| Почта и очереди | Ежедневно | rsync с жёсткими ссылками | 7 суток |
| Виртуальные машины | Раз в неделю | Снимок или экспорт образа | 4 копии |
| Логи и кэш | Не копировать | Исключения в списке | — |
Кэш, временные каталоги и содержимое /var/log раздувают копию в разы и почти никогда не нужны при восстановлении. Выносите их в список исключений с первого дня.
Инструменты
Для файлов берите restic или borg: оба дают дедупликацию, шифрование на стороне клиента и инкрементные снимки без полного перечитывания данных. Для баз — штатные дампы. Для выгрузки в облачное хранилище пригодится rclone, а выбор самого хранилища разобран в материале сравнение S3-совместимых хранилищ.
# restic: репозиторий в S3-совместимом хранилище
export RESTIC_REPOSITORY='s3:https://s3.example.net/backup-srv1'
export RESTIC_PASSWORD_FILE=/root/.restic-pass
restic init
# ежедневный инкремент файлов и конфигурации
restic backup /etc /var/www /home --exclude-file=/root/backup.exclude
# дамп базы прямо в поток, без промежуточного файла на диске
mysqldump --single-transaction --quick --all-databases \
| restic backup --stdin --stdin-filename all-databases.sql
# ретеншн и очистка
restic forget --keep-daily 14 --keep-weekly 8 --keep-monthly 12 --prune
# проверка целостности репозитория с чтением части данных
restic check --read-data-subset=5%
# список исключений пишем heredoc, чтобы не потерять шаблоны
cat > /root/backup.exclude << 'EOF'
/var/www/*/cache
/var/www/*/var/tmp
/var/log/journal
*.tmp
EOF
# borg: архив с компрессией и статистикой
borg create --stats --compression zstd,3 \
/mnt/backup::srv1-{now:%Y-%m-%d} /etc /var/www
# проверка архивов и список содержимого
borg check --verify-data /mnt/backup
borg list /mnt/backup
# восстановление одной базы из дампа
mysql shop < /root/restore/shop.sql
Куда складывать копии
Копия на том же массиве спасает только от ошибки оператора: пожар, кража или выход из строя контроллера уничтожат и данные, и копию. Минимально приемлемая схема — локальная копия для быстрого отката плюс вторая площадка. Дополнительный HDD на 1 ТБ за $15 в месяц удобен как локальный буфер, а опция бэкапа во внешнее хранилище за $10 в месяц закрывает вынос за пределы сервера.
Если на машине работает гипервизор, схему копий обычно строят на уровне виртуальных машин — как это делается, описано в материале Proxmox Backup Server. Отказ отдельного накопителя при этом остаётся отдельной процедурой и разобран в статье замена диска в RAID-массиве.
Проверка восстановления
Определите два числа и держите их в документации: RPO — сколько данных вы готовы потерять, RTO — за сколько обязаны подняться. Из них вытекает частота копий и способ восстановления. Дальше раз в месяц проделывайте упражнение целиком:
# поднимаем копию в отдельный каталог, не трогая боевые данные
restic restore latest --target /srv/restore-test --include /var/www
# сверяем файлы с боевыми, показываем только различия
diff -rq /var/www /srv/restore-test/var/www | head -n 20
# восстанавливаем базу в отдельную схему и считаем строки
mysql -e 'CREATE DATABASE shop_test;'
mysql shop_test < /root/restore/shop.sql
mysql -N -e 'SELECT COUNT(*) FROM shop_test.orders;' 2>&1
Самая частая причина потери данных не отказ диска, а копия, к которой имел доступ на удаление скомпрометированный сервер. Шифровальщик заходит по сохранённому ключу, стирает снимки в хранилище и оставляет только зашифрованные файлы. Закрывается это режимом только на добавление у учётной записи бэкапа, отдельным ключом доступа и второй копией, которую сервер вообще не видит. Вторая типичная ошибка — задание в cron, которое молча падает: если вывод уходит в /dev/null, вы узнаете о сломанном копировании в день аварии. Проверка: заведите отдельный мониторинг возраста последней копии и считайте задание сломанным, если свежего снимка нет более 26 часов.
Коротко
- RAID не бэкап: он защищает от отказа диска, а не от удаления и шифрования.
- Держите три копии на двух носителях, одну — за пределами сервера.
- Файлы копируйте restic или borg инкрементно, базы — дампом с ретеншном.
- Учётной записи бэкапа не давайте прав на удаление старых снимков.
- Раз в месяц восстанавливайте копию и сверяйте количество строк и файлов.
Готовые конфигурации с местом под локальный буфер копий и с опцией внешнего хранилища собраны в разделе выделенные серверы.