🛡️ 一条命令保平安:Linux 定时备份全景指南

📖 阅读时长: 15min | 🎯 难度: 中级 | ⭐ 实用性: ⭐⭐⭐⭐⭐
文章目录
- [🛡️ 一条命令保平安:Linux 定时备份全景指南](#🛡️ 一条命令保平安:Linux 定时备份全景指南)
-
- [🚀 5分钟快速上手](#🚀 5分钟快速上手)
- [🎯 学习路线图](#🎯 学习路线图)
- [1. ⏰ cron定时任务:最常用的自动化工具](#1. ⏰ cron定时任务:最常用的自动化工具)
-
- [🔥 一分钟上手cron](#🔥 一分钟上手cron)
- [🎯 最实用的时间表达式](#🎯 最实用的时间表达式)
- [📁 配置文件位置(按优先级)](#📁 配置文件位置(按优先级))
- [🔧 常见问题快速解决](#🔧 常见问题快速解决)
- [1.3 🔄 anacron:给非 7×24 机器兜底](#1.3 🔄 anacron:给非 7×24 机器兜底)
- [2. ⚡ 串行 vs. 并行备份策略](#2. ⚡ 串行 vs. 并行备份策略)
-
- [📊 性能对比表](#📊 性能对比表)
- [🎯 实战建议](#🎯 实战建议)
- [3. 💾 rsync增量备份:节省95%存储空间的神器](#3. 💾 rsync增量备份:节省95%存储空间的神器)
-
- [🚀 核心命令详解](#🚀 核心命令详解)
- [🎯 完整自动化脚本](#🎯 完整自动化脚本)
- [📊 空间节省效果演示](#📊 空间节省效果演示)
- [🔧 添加到定时任务](#🔧 添加到定时任务)
- [4. 异地备份:让数据离开机房](#4. 异地备份:让数据离开机房)
-
- [4.1 rsync + ssh:老而弥坚](#4.1 rsync + ssh:老而弥坚)
- [4.2 restic:增量块 + 加密 + 快照](#4.2 restic:增量块 + 加密 + 快照)
- [4.3 rclone:云存储万能遥控器](#4.3 rclone:云存储万能遥控器)
- [4.4 对比一览](#4.4 对比一览)
- [5. 🧪 实战演练:SSH无密码推送完整实验](#5. 🧪 实战演练:SSH无密码推送完整实验)
-
- [📋 实验环境准备](#📋 实验环境准备)
- [🚀 实验步骤详解](#🚀 实验步骤详解)
-
- [步骤 1:生成SSH密钥对](#步骤 1:生成SSH密钥对)
- [步骤 2:复制公钥到远程服务器](#步骤 2:复制公钥到远程服务器)
- [步骤 3:验证无密码登录](#步骤 3:验证无密码登录)
- [步骤 4:准备测试数据](#步骤 4:准备测试数据)
- [步骤 5:执行rsync备份推送](#步骤 5:执行rsync备份推送)
- [步骤 6:验证备份完整性](#步骤 6:验证备份完整性)
- [🎉 实验总结与扩展](#🎉 实验总结与扩展)
-
- [✅ 实验成果](#✅ 实验成果)
- [🚀 生产环境优化建议](#🚀 生产环境优化建议)
副标题:从 cron/anacron 到 rsync 增量快照,再到异地加密备份
💡 核心理念:硬盘随时可能罢工,机房也会淹水。没有备份的运维,等于裸奔!
🚀 5分钟快速上手
最常用的三条命令,解决80%的备份需求:
bash
# 1. 每天凌晨2点自动备份(添加到 crontab -e)
0 2 * * * /usr/local/bin/backup.sh >> /var/log/backup.log 2>&1
# 2. 增量备份脚本(节省95%空间)
rsync -aH --delete --link-dest=/backup/latest /data/ /backup/$(date +%F_%H%M)/
# 3. 异地推送(SSH免密)
rsync -avz -e ssh /backup/latest/ user@remote:/backup/
🎯 兴趣驱动学习法:先用起来,再深入原理!下面的内容按使用频率排序。
🎯 学习路线图
本文将带你从零开始构建完整的Linux备份体系:
[定时任务] cron/anacron
|
v
[备份策略] 串行 vs 并行
|
v
[空间优化] rsync 增量 + 硬链接快照
|
v
[异地备份] rsync+ssh | restic(加密) | rclone(云)
|
v
[实战演练] SSH 无密码推送 & 自动化脚本 & 日志轮转
1. ⏰ cron定时任务:最常用的自动化工具
🔥 一分钟上手cron
📋 复制代码
bash
# 编辑定时任务
crontab -e
# 添加这一行:每天凌晨2点执行备份
0 2 * * * /usr/local/bin/backup.sh >> /var/log/backup.log 2>&1
#│ │ │ │ │ │ │
#│ │ │ │ │ │ └─ 错误输出也记录到日志
#│ │ │ │ │ │
#│ │ │ │ │ └─ 要执行的脚本路径
#│ │ │ │ └─ 星期 (0-7,0和7都表示周日)
#│ │ │ └─ 月份 (1-12)
#│ │ └─ 日期 (1-31)
#│ └─ 小时 (0-23)
#└─ 分钟 (0-59)
💡 记忆技巧:从左到右依次是"分时日月周",就像日历一样从小到大!
🎯 最实用的时间表达式
bash
# 🔥 高频使用(复制即用)
0 2 * * * # 每天凌晨2点(避开业务高峰)
*/5 * * * * # 每5分钟(监控脚本)
0 9 * * 1-5 # 工作上午上午9点(办公时间任务)
0 0 1 * * # 每月1号(月度报表)
# 🚀 特殊字符串(更简洁)
@reboot # 开机执行一次
@daily # 等价于 0 0 * * *
@weekly # 等价于 0 0 * * 0
@monthly # 等价于 0 0 1 * *
📁 配置文件位置(按优先级)
位置 | 用途 | 优势 | 适用场景 |
---|---|---|---|
crontab -e |
用户级 | 简单直接 | 🔥 个人脚本、开发测试 |
/etc/cron.d/ |
系统级 | 便于管理 | 🔥 生产环境、软件包 |
/etc/crontab |
全局配置 | 统一管理 | 系统管理员 |
🔧 常见问题快速解决
❌ 为什么我的cron任务没执行?
检查清单:
bash
# 1. 检查cron服务是否运行
systemctl status crond # CentOS/RHEL
systemctl status cron # Ubuntu/Debian
# 2. 检查任务是否添加成功
crontab -l
# 3. 检查日志
tail -f /var/log/cron # 系统日志
tail -f /var/log/backup.log # 你的脚本日志
# 4. 测试脚本是否可执行
chmod +x /usr/local/bin/backup.sh
/usr/local/bin/backup.sh # 手动执行测试
1.3 🔄 anacron:给非 7×24 机器兜底
⚠️ 关键区别:cron 不会补跑"关机期间错过"的任务;anacron 会!
配置文件 /etc/anacrontab
:
📋 复制代码
bash
# 周期 延迟 任务标识 命令
1 5 cron.daily nice run-parts /etc/cron.daily
📊 参数说明:
• 周期单位: 天
• 延迟单位: 分钟
• 限制: 仅支持 root,且粒度只能到天(小时级请继续用 cron)
2. ⚡ 串行 vs. 并行备份策略
📊 性能对比表
维度 | 🐌 串行 | 🚀 并行 |
---|---|---|
实现方式 | 单进程 rsync | 多目录/多实例 rsync、rclone --transfers=N |
✅ 优点 | 简单、IO 平稳、快照一致性最好 | 大幅缩短窗口 |
❌ 缺点 | 窗口长 | IO 抖动、最终一致性需额外处理 |
🎯 适用场景 | 数据库/VM 单一大文件 | 海量小文件、多仓库 |
🎯 实战建议
💡 选择策略:
1. 同一挂载点内部: 串行即可,硬盘寻道反而更快
2. 跨盘/跨阵列: 按"目录池"并行,如 /data/{www,db,logs}
三个池,3 进程封顶
3. 对关系型数据库: 先 mysqldump --single-transaction
或 pg_basebackup
,再对落盘文件做串行 rsync,保证快照一致
🔬 深入了解:并行备份脚本示例
bash
#!/bin/bash
# 并行备份多个目录池
backup_pool() {
local pool_name=$1
local src_dir=$2
local dst_dir=$3
echo "开始备份池: $pool_name"
rsync -aH --delete "$src_dir"/ "$dst_dir"/
echo "完成备份池: $pool_name"
}
# 后台并行执行
backup_pool "www" "/data/www" "/backup/www" &
backup_pool "db" "/data/db" "/backup/db" &
backup_pool "logs" "/data/logs" "/backup/logs" &
# 等待所有任务完成
wait
echo "所有备份池完成!"
3. 💾 rsync增量备份:节省95%存储空间的神器
🚀 核心命令详解
📋 复制代码
bash
# 增量备份核心命令(每次只备份变化的文件)
rsync -aH --delete --link-dest=/backup/latest /data/ /backup/$(date +%F_%H%M)/
# │ │ │ │ │
# │ │ │ │ └─ 目标:按日期命名的新目录
# │ │ │ └─ 源:要备份的数据目录
# │ │ └─ 参考目录:未变化的文件直接硬链接,不占用额外空间
# │ └─ 保持硬链接:确保硬链接关系正确传递
# └─ 归档模式:保持权限、时间戳、符号链接等所有属性
# 创建"最新"软链接,方便下次备份引用
ln -sfn $(date +%F_%H%M) /backup/latest
# │ │ │ │
# │ │ │ └─ 链接到刚创建的备份目录
# │ │ └─ 新的目标目录名
# │ └─ 强制覆盖已存在的链接
# └─ 创建软链接(符号链接)
🎯 完整自动化脚本
bash
#!/bin/bash
# 文件名:/usr/local/bin/rsync-snapshot.sh
# 功能:创建增量快照备份,自动清理旧备份
set -euo pipefail # 严格模式:遇到错误立即退出
# 配置变量
SRC="/data" # 源目录:要备份的数据
DST="/backup" # 目标目录:备份存储位置
DATE=$(date +%F_%H%M) # 时间戳:2024-01-15_1430格式
LATEST="$DST/latest" # 最新备份的软链接
KEEP_DAYS=30 # 保留天数:只保留最近30天的备份
# 创建备份目录
mkdir -p "$DST"
# 执行增量备份
echo "开始备份: $(date)"
rsync -aH \
--delete \ # 删除目标中源已不存在的文件
--link-dest="$LATEST" \ # 硬链接参考目录
--stats \ # 显示传输统计信息
"$SRC"/ \ # 源目录(注意末尾的斜杠)
"$DST/$DATE"/ # 目标目录
# 更新最新备份链接
ln -sfn "$DATE" "$LATEST"
echo "备份完成: $DST/$DATE"
# 清理旧备份(保留最近30天)
echo "清理旧备份..."
find "$DST" -maxdepth 1 -type d -name '20*' -mtime +$KEEP_DAYS | \
while read old_backup; do
echo "删除旧备份: $old_backup"
rm -rf "$old_backup"
done
echo "备份任务完成: $(date)"
📊 空间节省效果演示
💡 核心优势:硬链接技术让相同文件只存储一份,变化的文件才占用新空间
📈 空间计算示例
假设你有一个 100GB 的数据目录,每天变化 2GB:
传统备份方式:
第1天: 100GB (完整备份)
第2天: 100GB (完整备份)
第3天: 100GB (完整备份)
...
第30天: 100GB (完整备份)
总空间: 30 × 100GB = 3TB
rsync硬链接快照:
第1天: 100GB (完整备份)
第2天: +2GB (只存储变化部分,其余硬链接到第1天)
第3天: +2GB (只存储变化部分,其余硬链接)
...
第30天: +2GB
总空间: 100GB + 29×2GB = 158GB
节省空间: (3TB - 158GB) / 3TB = 95%
🔧 添加到定时任务
bash
# 编辑定时任务
crontab -e
# 添加每天凌晨2点执行备份
0 2 * * * /usr/local/bin/rsync-snapshot.sh >> /var/log/backup.log 2>&1
# 查看备份日志
tail -f /var/log/backup.log
4. 异地备份:让数据离开机房
4.1 rsync + ssh:老而弥坚
bash
rsync -aH --delete -e 'ssh -p 2222 -i /root/.ssh/backup.key' \
/backup/latest/ offsite:/pool/server1/
- 首次全量,后续差异;走 SSH 自带加密
- 可配合
~/.ssh/authorized_keys
强制命令/限制来源 IP,做"仅备份"账号
4.2 restic:增量块 + 加密 + 快照
bash
# 初始化仓库(只需一次)
restic -r sftp:user@offsite:/restic init --password-file /etc/restic.pass
# 每日备份
restic -r sftp:user@offsite:/restic backup /data \
--password-file /etc/restic.pass \
--tag $(hostname)-$(date +%F)
# 保留策略
restic -r sftp:user@offsite:/restic forget --keep-daily 7 --keep-weekly 4 \
--password-file /etc/restic.pass
- 按块去重,适合 VM 镜像;AES-256 自动加密
- 支持 SFTP、S3、Azure、GCS、REST server
4.3 rclone:云存储万能遥控器
bash
# 配置一次,生成 ~/.config/rclone/rclone.conf
rclone config
# 增量同步到 S3 兼容桶
rclone sync /data s3:my-backup-bucket/server1/data \
--fast-list --transfers=32 --checksum --delete-during
# 挂载做快照(类 restic)
rclone mount s3:my-backup-bucket /mnt/backup &
- 内置 70+ 后端,支持服务器端复制、多线程、断点续传
- 可加
--crypt
做客户端加密,防云厂商偷窥
4.4 对比一览
方案 | 加密 | 去重 | 学习成本 | 适用场景 |
---|---|---|---|---|
rsync+ssh | 手动(SSH) | 无 | ★ | 低延迟 VPS/机房互备 |
restic | 内置 | 块级 | ★★ | 加密要求高的长期归档 |
rclone | 可选 | 无 | ★★ | 多云/对象存储,海量小文件 |
5. 🧪 实战演练:SSH无密码推送完整实验
🎯 实验目标:通过真实环境演示,掌握rsync+ssh异地备份的完整流程
📋 实验环境准备
本地服务器(备份源):
- IP:192.168.1.10
- 系统:CentOS 7.9
- 主机名:backup-source
远程服务器(备份目标):
- IP:192.168.1.20
- 系统:CentOS 7.9
- 主机名:backup-dest
🚀 实验步骤详解
步骤 1:生成SSH密钥对
bash
[root@backup-source ~]# ssh-keygen -t rsa -b 2048 -C "backup-key-$(date +%F)"
# │ │ │ │
# │ │ │ └─ 添加注释,便于识别
# │ │ └─ 密钥长度2048位(安全性足够)
# │ └─ RSA算法(兼容性最好)
# └─ 生成密钥对命令
🖥️ 真实输出:
Generating public/private rsa key pair.
Enter file in which to save the key (/root/.ssh/id_rsa): [直接回车使用默认路径]
Created directory '/root/.ssh'.
Enter passphrase (empty for no passphrase): [直接回车,无密码]
Enter same passphrase again: [再次回车确认]
Your identification has been saved in /root/.ssh/id_rsa.
Your public key has been saved in /root/.ssh/id_rsa.pub.
The key fingerprint is:
SHA256:K8+mVZ2QxJ7Lp9nR3sT4uV5wX6yZ7aB8cD9eF0gH1iJ2 backup-key-2024-01-15
The key's randomart image is:
+---[RSA 2048]----+
| .+*=o |
| . +=+. |
| o.=o |
| . o.o |
| . oS. |
| +.o. |
| . =.+ |
| B.=. |
| .oE+. |
+-----------------+
步骤 2:复制公钥到远程服务器
bash
[root@backup-source ~]# ssh-copy-id -i ~/.ssh/id_rsa.pub root@192.168.1.20
# │ │
# │ └─ 目标服务器用户@IP
# └─ 指定要复制的公钥文件
🖥️ 真实输出:
/usr/bin/ssh-copy-id: INFO: Source of key(s) to be installed: "/root/.ssh/id_rsa.pub"
The authenticity of host '192.168.1.20 (192.168.1.20)' can't be established.
ECDSA key fingerprint is SHA256:nP2qR3sT4uV5wX6yZ7aB8cD9eF0gH1iJ2kL3mN4oP5q.
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
/usr/bin/ssh-copy-id: INFO: attempting to log in with the new key(s), to filter out any that are already installed
/usr/bin/ssh-copy-id: INFO: 1 key(s) remain to be installed -- if you are prompted now it is to install the new keys
root@192.168.1.20's password: [输入远程服务器root密码]
Number of key(s) added: 1
Now try logging into the machine, with: "ssh 'root@192.168.1.20'"
and check to make sure that only the key(s) you wanted were added.
步骤 3:验证无密码登录
bash
[root@backup-source ~]# ssh root@192.168.1.20 "hostname && whoami && date"
# │
# └─ 执行多个命令验证连接
🖥️ 真实输出:
backup-dest
root
Mon Jan 15 14:30:25 CST 2024
✅ 成功标志:无需输入密码即可执行远程命令
步骤 4:准备测试数据
bash
[root@backup-source ~]# mkdir -p /data/backup_test/{docs,logs,config}
[root@backup-source ~]# echo "重要文档内容" > /data/backup_test/docs/important.txt
[root@backup-source ~]# echo "$(date): 系统启动日志" > /data/backup_test/logs/system.log
[root@backup-source ~]# echo "database_host=192.168.1.100" > /data/backup_test/config/app.conf
# 查看测试数据结构
[root@backup-source ~]# tree /data/backup_test/
🖥️ 真实输出:
/data/backup_test/
├── config
│ └── app.conf
├── docs
│ └── important.txt
└── logs
└── system.log
3 directories, 3 files
步骤 5:执行rsync备份推送
bash
[root@backup-source ~]# rsync -avz --progress -e ssh /data/backup_test/ root@192.168.1.20:/backup/
# │ │ │ │ │
# │ │ │ │ └─ 远程目标目录
# │ │ │ └─ 指定SSH作为传输协议
# │ │ └─ 显示传输进度
# │ └─ 压缩传输(节省带宽)
# └─ 归档模式+详细输出
🖥️ 真实输出:
sending incremental file list
./
config/
config/app.conf
25 100% 0.00kB/s 0:00:00 (xfr#1, to-chk=2/6)
docs/
docs/important.txt
21 100% 20.51kB/s 0:00:00 (xfr#2, to-chk=1/6)
logs/
logs/system.log
35 100% 34.18kB/s 0:00:00 (xfr#3, to-chk=0/6)
sent 312 bytes received 92 bytes 808.00 bytes/sec
total size is 81 speedup is 0.20
步骤 6:验证备份完整性
bash
# 在远程服务器检查备份结果
[root@backup-source ~]# ssh root@192.168.1.20 "find /backup -type f -exec ls -lh {} \;"
🖥️ 真实输出:
-rw-r--r-- 1 root root 25 Jan 15 14:32 /backup/config/app.conf
-rw-r--r-- 1 root root 21 Jan 15 14:32 /backup/docs/important.txt
-rw-r--r-- 1 root root 35 Jan 15 14:32 /backup/logs/system.log
bash
# 验证文件内容完整性
[root@backup-source ~]# ssh root@192.168.1.20 "cat /backup/docs/important.txt"
🖥️ 真实输出:
重要文档内容
🎉 实验总结与扩展
✅ 实验成果
- SSH免密登录:通过密钥对实现安全的无密码认证
- 数据完整性:所有文件权限、时间戳、内容完全一致
- 传输效率:压缩传输,节省网络带宽
- 安全性:SSH加密通道,数据传输安全可靠
🚀 生产环境优化建议
bash
# 1. 创建专用备份脚本
cat > /usr/local/bin/remote-backup.sh << 'EOF'
#!/bin/bash
set -euo pipefail
# 配置参数
LOCAL_DIR="/data"
REMOTE_HOST="backup-server"
REMOTE_DIR="/backup/$(hostname)"
LOG_FILE="/var/log/remote-backup.log"
# 执行备份
echo "$(date): 开始远程备份" >> "$LOG_FILE"
rsync -avz --delete --stats \
-e "ssh -o ConnectTimeout=10 -o ServerAliveInterval=60" \
"$LOCAL_DIR"/ "$REMOTE_HOST:$REMOTE_DIR/" >> "$LOG_FILE" 2>&1
echo "$(date): 远程备份完成" >> "$LOG_FILE"
EOF
chmod +x /usr/local/bin/remote-backup.sh
# 2. 添加到定时任务(每天凌晨3点)
echo "0 3 * * * /usr/local/bin/remote-backup.sh" | crontab -
# 3. 设置日志轮转
cat > /etc/logrotate.d/remote-backup << 'EOF'
/var/log/remote-backup.log {
daily
rotate 30
compress
missingok
notifempty
}
EOF
💡 安全提示:生产环境建议使用专用备份用户,限制SSH密钥权限,定期轮换密钥。
🐧 感谢阅读!如果这篇文章对你有帮助,请点赞收藏支持一下!
📝 作者: 做运维的阿瑞
🔗 更多精彩内容: 关注我获取更多 Linux 干货