Бекапы докер контейнеров с Offen

В этой статье мы разберём, как настроить ежедневное резервное копирование Docker-томов с отправкой в S3-хранилище и уведомлениями через Email и Telegram. В качестве инструмента будем использовать Offen/docker-volume-backup.
Пример конфигурации Docker Compose
Создайте файл docker-compose.yml
со следующим содержимым:
version: '3.8'
services:
postgres:
image: postgres:15
volumes:
- pg_data:/var/lib/postgresql/data
environment:
POSTGRES_PASSWORD: example
restart: unless-stopped
backup:
image: offen/docker-volume-backup:latest
restart: unless-stopped
depends_on:
- postgres
volumes:
- /etc/timezone:/etc/timezone:ro
- /etc/localtime:/etc/localtime:ro
- pg_data:/backup/pg_data:ro
- /var/run/docker.sock:/var/run/docker.sock
environment:
# Настройка расписания (каждый день в 2:00)
BACKUP_CRON_EXPRESSION: "0 2 * * *"
# Указание томов для бэкапа
BACKUP_SOURCES: "/backup/pg_data"
# Настройка S3
AWS_ACCESS_KEY_ID: ${AWS_ACCESS_KEY_ID}
AWS_SECRET_ACCESS_KEY: ${AWS_SECRET_ACCESS_KEY}
AWS_S3_BUCKET_NAME: ${AWS_S3_BUCKET_NAME}
AWS_ENDPOINT: ${AWS_ENDPOINT}
# Уведомления по Email
# NOTIFICATION_URLS: "smtp://${SMTP_USERNAME}:${SMTP_PASSWORD}@${SMTP_HOST}:${SMTP_PORT}/?fromAddress=${SMTP_FROM}&toAddresses=${TO_SENT_EMAIL}"
# Уведомления в Telegram
NOTIFICATION_LEVEL: "info"
NOTIFICATION_URLS: "telegram://${TELEGRAM_TOKEN}@telegram?chats=${TELEGRAM_USER_ID}"
# Дополнительные настройки
BACKUP_FILENAME: "backup-$(date +%Y-%m-%d).tar.gz"
BACKUP_RETENTION_DAYS: 7
volumes:
pg_data:
Для безопасного хранения переменных используйте переменные окружения или файл .env в той же папке где находится ваш docker-compose.yaml файл.
Пример файла .env:
SMTP_PORT="465"
SMTP_HOST="smtp.example.com"
SMTP_FROM="[email protected]"
SMTP_USERNAME="[email protected]""
SMTP_PASSWORD="strongpPassword"
TO_SENT_EMAIL="[email protected]"
AWS_ACCESS_KEY_ID="asdfjksaghdf"
AWS_SECRET_ACCESS_KEY="sakjdfjkl"
AWS_S3_BUCKET_NAME="docker-backup"
AWS_ENDPOINT="s3.aws.com"
TELEGRAM_TOKEN="sadnljkhjlkf"
TELEGRAM_USER_ID="21341234"
Пояснение конфигурации
1. Сервис приложения (PostgreSQL)
- Использует том
pg_data
для хранения данных. - Том будет доступен для чтения сервису бэкапа.
2. Сервис резервного копирования
- Расписание:
BACKUP_CRON_EXPRESSION
задаёт ежедневное выполнение в 2:00. - S3-хранилище: Укажите свои AWS-ключи, имя бакета и регион.
- Уведомления:
- Email: Используется SMTP-сервер с параметрами авторизации.
- Telegram:
- Замените TELEGRAM_TOKEN на токен вашего бота.
- TELEGRAM_USER_ID можно получить через @userinfobot в Telegram.
- Хранение бэкапов:
BACKUP_RETENTION_DAYS
автоматически удаляет старые копии.
Настройка уведомлений
Для Telegram:
- Создайте бота через @BotFather и получите токен.
- Узнайте ID чата через @userinfobot.
- Укажите параметры в формате:
NOTIFICATION_URL="telegram://123456:ABC-DEF1234ghIkl-zyx57W2v1u123ew11@telegram/?chats=123456789"
Запуск системы
- Замените все переменные (AWS_SECRET_ACCESS_KEY, TELEGRAM_TOKEN и др.) на реальные значения.
- Выполните команду:
docker-compose up -d
- Для тестирования выполните бэкап вручную:
docker-compose exec backup backup
Преимущества решения
- Автоматизация: Ежедневные бэкапы без ручного вмешательства.
- Надёжность: Хранение в S3 с версионированием и lifecycle-правилами.
- Мониторинг: Мгновенные уведомления о статусе операций.
- Гибкость: Поддержка шифрования (добавьте
BACKUP_ENCRYPTION_KEY
для включения шифрования бекапов).
Используя этот подход, вы защитите данные ваших Docker-приложений от потери. Дополнительные настройки (например, резервные копии в несколько хранилищ) можно найти в официальной документации.
BONUS
Шифрование и расшифровка бэкапов в Offen/docker-volume-backup
Offen/docker-volume-backup поддерживает сквозное шифрование резервных копий с помощью алгоритма AES-256-GCM. Это обеспечивает защиту данных даже при компрометации S-хранилища.
1. Настройка шифрования
Шаг 1: Генерация ключа
Ключ должен быть 32-байтной строкой в формате Base64 или Hex. Пример генерации:
# Генерация в Base64
openssl rand -base64 32 > backup-key.txt
# Или в Hex
openssl rand -hex 32 > backup-key.txt
Шаг 2: Добавление ключа в конфигурацию
В сервисе backup
файла docker-compose.yml
укажите:
environment:
BACKUP_ENCRYPTION_KEY: "file:/backup-key.txt" # Путь внутри контейнера
# Или напрямую (не рекомендуется для продакшена):
# BACKUP_ENCRYPTION_KEY: "your-encryption-key-in-base64-or-hex"
Шаг 3: Монтирование ключа
Добавьте volume для файла с ключом:
volumes:
- ./backup-key.txt:/backup-key.txt:ro
2. Как это работает
- Архив шифруется перед отправкой в S3
- Используется гибридная схема:
- Случайный ключ данных (DEK) генерируется для каждого бэкапа
- DEK шифруется главным ключом (BACKUP_ENCRYPTION_KEY)
- Зашифрованный DEK сохраняется в метаданных архива
- Алгоритм: AES-256-GCM (аутентифицированное шифрование)
3. Расшифровка бэкапов
Вариант 1: Через утилиту docker-volume-backup
docker run --rm -v /path/to/backup.tar.gz.gpg:/backup.tar.gz.gpg \
-v /path/to/backup-key.txt:/backup-key.txt \
offen/docker-volume-backup:latest decrypt \
--input /backup.tar.gz.gpg \
--output /backup.tar.gz \
--key-file /backup-key.txt
Вариант 2: Вручную с OpenSSL
Для ключа в Hex-формате:
openssl enc -d -aes-256-gcm \
-in backup.tar.gz.gpg \
-out backup.tar.gz \
-K "$(cat backup-key.txt)" \
-iv <(head -c 16 backup.tar.gz.gpg) \
-aad <(tail -c +17 backup.tar.gz.gpg | head -c 24)
4. Важные особенности
- Хранение ключа:
- Никогда не коммитьте ключ в Git
- Используйте секреты Docker или KMS (AWS Secrets Manager, HashiCorp Vault)
- Регулярно ротируйте ключи (но старые бэкапы потребуют старых ключей!)
- Метаданные:
- Имена файлов в S3 не шифруются
- Для полной анонимизации используйте
BACKUP_FILENAME_ENCRYPTED=true
Производительность:
Тестовые данные: 1 ГБ
Шифрование: ~15 сек (на CPU Intel i7)
Дешифровка: ~12 сек
5. Пример полной конфигурации
services:
backup:
image: offen/docker-volume-backup:latest
environment:
BACKUP_ENCRYPTION_KEY: "file:/secrets/backup-key.txt"
BACKUP_FILENAME_ENCRYPTED: "true" # Случайное имя файла
volumes:
- ./secrets/backup-key.txt:/secrets/backup-key.txt:ro
6. Сценарии восстановления
Если ключ утерян:
- Данные невозможно восстановить
- Решение:
- Хранить ключ в 3х местах (USB-накопитель, бумажный носитель, облако)
- Использовать аппаратные HSM для enterprise-решений
При компрометации ключа:
- Сгенерировать новый ключ
- Перешифровать старые бэкапы новым ключом
- Удалить старый ключ из всех систем
Рекомендации
- Тестируйте восстановление перед инцидентом
- Используйте разные ключи для окружений (prod/stage/dev)
- Включите версионирование в S3 для защиты от ransomware-атак
Шифрование в Offen/docker-volume-backup даёт enterprise-уровень защиты при минимальных настройках. Главное — обеспечить сохранность ключей!