#!/bin/bash
# backup.sh
# 用法:./backup.sh <來源目錄> [保留天數]
# 例:./backup.sh /var/lib/mysql 7
set -euo pipefail
SRC_DIR=${1:?請指定來源目錄}
RETENTION_DAYS=${2:-7}
BACKUP_ROOT="/backup"
DATE=$(date '+%Y%m%d')
TIMESTAMP=$(date '+%Y%m%d_%H%M%S')
DEST_DIR="$BACKUP_ROOT/$(basename "$SRC_DIR")"
LOG_FILE="$DEST_DIR/${TIMESTAMP}.log"
mkdir -p "$DEST_DIR"
# 記錄開始
echo "=== 備份開始 $(date '+%F %T') ===" | tee -a "$LOG_FILE"
echo "來源: $SRC_DIR" | tee -a "$LOG_FILE"
echo "目標: $DEST_DIR/${DATE}.tar.gz" | tee -a "$LOG_FILE"
# 執行備份(排除臨時檔、鎖檔等)
tar -czf "$DEST_DIR/${DATE}.tar.gz" \
--exclude="*.tmp" \
--exclude="*~" \
--exclude="*.lock" \
-C "$(dirname "$SRC_DIR")" "$(basename "$SRC_DIR")" \
>> "$LOG_FILE" 2>&1
TAR_EXIT=$?
if [ $TAR_EXIT -eq 0 ]; then
echo "=== 備份成功 $(date '+%F %T') ===" | tee -a "$LOG_FILE"
else
echo "=== 備份失敗 (exit $TAR_EXIT) $(date '+%F %T') ===" | tee -a "$LOG_FILE"
exit $TAR_EXIT
fi
# 清理過期備份
OLD_DATE=$(date -d "$DATE - $RETENTION_DAYS days" '+%Y%m%d')
OLD_FILE="$DEST_DIR/${OLD_DATE}.tar.gz"
if [ -f "$OLD_FILE" ]; then
rm -f "$OLD_FILE"
echo "已刪除過期備份: $OLD_FILE" | tee -a "$LOG_FILE"
else
echo "無過期備份需刪除 ($OLD_FILE 不存在)" | tee -a "$LOG_FILE"
fi
echo "=== 備份任務結束 ===" | tee -a "$LOG_FILE"
mkdir -p /usr/local/sbin
vim /usr/local/sbin/backup.sh
chmod +x /usr/local/sbin/backup.sh
mkdir -p /backup
chmod 750 /backup
vim /etc/crontab
# 每天凌晨 3:00 備份 MySQL 資料目錄,保留 7 天
0 3 * * * root /usr/local/sbin/backup.sh /var/lib/mysql 7
# 每天 4:00 備份網站代碼,保留 30 天
0 4 * * * root /usr/local/sbin/backup.sh /var/www/html 30
service crond restart
chkconfig crond on
# 或 systemctl enable --now crond
#!/bin/bash
# backup_mysql.sh
DB_USER="backup_user"
DB_PASS="strong_password"
DB_HOST="localhost"
BACKUP_DIR="/backup/mysql"
RETENTION=7
DATE=$(date '+%Y%m%d_%H%M%S')
mkdir -p "$BACKUP_DIR"
# 使用 mysqldump --single-transaction 獲得一致性快照
mysqldump -u"$DB_USER" -p"$DB_PASS" -h"$DB_HOST" \
--single-transaction --routines --triggers --events \
--all-databases | gzip > "$BACKUP_DIR/mysql_${DATE}.sql.gz"
# 清理
find "$BACKUP_DIR" -name "mysql_*.sql.gz" -mtime +$RETENTION -delete
# 本地推送到遠端備份伺服器
rsync -avz --delete /backup/ user@backupsrv:/remote/backup/$(hostname)/
# 或遠端拉取(備份伺服器主動連線)
rsync -avz user@web:/backup/ /remote/backup/web/
cron 的 MAILTO 或自定義郵件發送告警。tar -tzf backup.tar.gz >/dev/null。「tar 打包 + crontab 定時 + find 清理 + 日誌留痕 + 校驗告警」構成最小可用備份體系。根據業務 RPO/RTO 要求,逐步升級為 mysqldump 熱備份、rsync 異地增量、專業備份軟體(Bacula、Restic、Veeam),但核心邏輯不變:自動化、可驗證、可追溯。