Edit: /opt/canhelp/scripts/backup.sh (3132B)
#!/usr/bin/env bash
# =============================================================================
# backup.sh — резервное копирование БД и uploads
# Использование:
# scripts/backup.sh — создать бэкап прямо сейчас
# scripts/backup.sh --restore — восстановить последний бэкап
# scripts/backup.sh --list — список бэкапов
# Добавить в cron (ежедневно в 3:00):
# 0 3 * * * /opt/canhelp/scripts/backup.sh >> /opt/canhelp/backups/cron.log 2>&1
# =============================================================================
set -euo pipefail
APP_DIR="/opt/canhelp"
BACKUP_DIR="$APP_DIR/backups"
KEEP_DAYS=14
TIMESTAMP=$(date '+%Y%m%d_%H%M%S')
DB_NAME="canhelp"
DB_USER="canhelp"
mkdir -p "$BACKUP_DIR"
case "${1:-}" in
--restore)
LATEST=$(ls -t "$BACKUP_DIR"/*.sql.gz 2>/dev/null | head -1)
if [[ -z "$LATEST" ]]; then
echo "ОШИБКА: бэкапы не найдены в $BACKUP_DIR"
exit 1
fi
echo "==> Восстановление из: $LATEST"
read -rp "Вы уверены? Это перезапишет БД '$DB_NAME' [y/N]: " confirm
[[ "$confirm" == "y" || "$confirm" == "Y" ]] || exit 0
gunzip -c "$LATEST" | docker compose -f "$APP_DIR/docker-compose.yml" exec -T db \
psql -U "$DB_USER" -d "$DB_NAME"
echo "✓ Восстановление завершено"
;;
--list)
echo "Бэкапы в $BACKUP_DIR:"
ls -lh "$BACKUP_DIR"/*.sql.gz 2>/dev/null || echo " (нет бэкапов)"
;;
*)
# ─── Бэкап БД ─────────────────────────────────────────────────────────────
DB_FILE="$BACKUP_DIR/db_${TIMESTAMP}.sql.gz"
echo "==> Дамп базы данных → $DB_FILE"
docker compose -f "$APP_DIR/docker-compose.yml" exec -T db \
pg_dump -U "$DB_USER" "$DB_NAME" | gzip > "$DB_FILE"
echo " $(du -h "$DB_FILE" | cut -f1) сохранено"
# ─── Бэкап uploads ────────────────────────────────────────────────────────
UPLOADS_FILE="$BACKUP_DIR/uploads_${TIMESTAMP}.tar.gz"
if [[ -d "$APP_DIR/apps/api/uploads" ]]; then
echo "==> Архив uploads → $UPLOADS_FILE"
tar -czf "$UPLOADS_FILE" -C "$APP_DIR/apps/api" uploads
echo " $(du -h "$UPLOADS_FILE" | cut -f1) сохранено"
fi
# ─── Очистка старых бэкапов ───────────────────────────────────────────────
echo "==> Удаление бэкапов старше ${KEEP_DAYS} дней"
find "$BACKUP_DIR" -name "*.gz" -mtime "+${KEEP_DAYS}" -delete
echo ""
echo "✓ Бэкап завершён: $TIMESTAMP"
ls -lh "$BACKUP_DIR"/*.gz 2>/dev/null | tail -4
;;
esac