Что именно нужно копировать
Список того, что действительно надо сохранять на VDS, что копировать бессмысленно и как выгружать базы данных, чтобы копия оказалась рабочей.
Обновлено 23 августа 2026 г.
Автоматических резервных копий машины у нас нет: снимков состояния в панели тоже нет, а переустановка системы стирает диск целиком. Значит, копии — целиком ваша задача, и начинать её надо в первый день, а не после потери.
Что копировать обязательно
- Данные приложений — тома Docker, каталоги сайтов, загруженные файлы пользователей.
- Выгрузки баз данных — именно выгрузки, а не файлы базы на ходу (об этом ниже).
- Настройки —
/etc/nginx,/etc/caddy, юниты systemd, файлыcompose.yamlи.env, правила брандмауэра. - Сертификаты и ключи —
/etc/letsencrypt, ключи приложений, ключи DKIM почтового сервера. - Задания по расписанию —
crontab -l > /root/crontab.txtперед копированием, иначе восстановите всё, кроме расписания. - Список установленных пакетов —
dpkg --get-selections > /root/packages.txt. Занимает килобайты, экономит часы.
Что копировать не нужно
Система, пакеты и образы Docker восстанавливаются переустановкой и командами — они не стоят места и времени. Не копируйте /proc, /sys, /dev, /var/lib/docker целиком, каталоги кеша и файлы подкачки.
Разумный ориентир: копия должна содержать всё, чего нет в интернете и что вы не сможете воссоздать по инструкции.
Базы данных
Файлы работающей базы копировать нельзя: получится снимок в середине записи, который может не открыться. Правильный путь — выгрузка средствами самой базы.
docker compose exec -T db pg_dump -U postgres app | gzip > /backup/app-$(date +%F).sql.gz
docker compose exec -T db mysqldump -u root -p"$MYSQL_ROOT_PASSWORD" --single-transaction app | gzip > /backup/app-$(date +%F).sql.gz
sqlite3 /data/app.db ".backup '/backup/app-$(date +%F).db'"
Для PostgreSQL и MySQL останавливать сервис не нужно. Для SQLite используйте .backup, а не cp: копирование файла на ходу даёт битую базу.
Копия, из которой ни разу не восстанавливали, копией не считается. Проверьте её на пустой машине или в отдельном контейнере — см. учебное восстановление.
Пример полного набора
#!/bin/bash
set -euo pipefail
DEST=/backup/$(date +%F)
mkdir -p "$DEST"
docker compose -f /opt/myapp/compose.yaml exec -T db pg_dump -U postgres app | gzip > "$DEST/db.sql.gz"
tar czf "$DEST/etc.tar.gz" /etc/nginx /etc/letsencrypt /opt/myapp/compose.yaml /opt/myapp/.env
tar czf "$DEST/uploads.tar.gz" /var/www/uploads
crontab -l > "$DEST/crontab.txt"
dpkg --get-selections > "$DEST/packages.txt"
Скрипт кладут в /usr/local/bin/backup.sh, дают права chmod 700 и ставят в расписание. Дальше копию нужно отправить на другую площадку — файл рядом с данными не защищает ни от чего.
Сколько хранить
Правило «3-2-1» в упрощённом виде: не меньше двух копий, минимум одна вне этой машины. По срокам достаточно семи ежедневных, четырёх еженедельных и трёх ежемесячных — этого хватает, чтобы откатиться к состоянию до тихой поломки, которую заметили не сразу.
Место считайте заранее: на VDS-1 диск 40 ГБ, и хранить историю копий на нём же попросту негде — см. место на диске.
Частые ошибки
- Копия лежит на той же машине. Переустановка, потеря доступа, ошибка
rm -rf— и копии нет вместе с данными. - Забыли
.env. Данные есть, а пароли и ключи к ним утрачены. - Копируют том с базой на ходу. Восстановление падает на повреждённом файле. Только выгрузка.
- Никто не знает, что копия перестала создаваться. Настройте push-проверку в Uptime Kuma: скрипт после успеха дёргает адрес, молчание сутки — тревога.