rsync —— 增量同步的事实标准
rsync —— 增量同步的事实标准
分类:03 文件与传输 适用:Linux / macOS / Windows(cwRsync),协议 30/31 一句话:只传差异、能断点续传、能镜像删除,备份与发布的默认选择。
1. 它解决什么问题
- 几 GB 目录每天同步,只改了几 MB,不想全量传。
- 迁移服务器,要保留权限、属主、软链接、时间戳。
- 做镜像站点,源端删了目标端也要删。
- 限速同步,避免备份把业务带宽打满。
2. 安装
apt install -y rsync
dnf install -y rsync
apk add rsync
# Windows 用 cwRsync 或 WSL
两端版本差异太大时会提示协议不兼容,尽量保持 3.x。
3. 语法与最容易踩的斜杠
rsync [选项] 源 目标
rsync -av /data/ /backup/data/ # 同步 /data 的内容到 /backup/data
rsync -av /data /backup/ # 同步 /data 目录本身 → /backup/data
| 写法 | 结果 |
|---|---|
/data/ |
复制目录内容 |
/data |
复制目录本身(目标下会多一层 data) |
这条规则是 rsync 事故的头号来源。不确定就加 -n 先看。
4. 核心选项
| 选项 | 含义 | 备注 |
|---|---|---|
-a |
归档模式 = -rlptgoD |
保留软链、权限、时间、属主、设备 |
-v |
详细 | -vv 更细 |
-z |
传输压缩 | 内网高带宽可关掉,省 CPU |
-P |
--partial --progress |
断点续传 + 进度条 |
-n / --dry-run |
试运行 | 危险操作前必加 |
--delete |
删除目标端多余文件 | 镜像同步 |
--delete-after |
传输完再删 | 比默认更安全 |
--delete-excluded |
连被排除的文件也从目标删 | 慎用 |
--exclude |
排除模式 | 可多次 |
--include |
包含模式 | 与 exclude 有顺序 |
--exclude-from=file |
从文件读排除规则 | |
--filter |
完整过滤语法 | 最灵活 |
-e ssh |
指定远程 shell | -e 'ssh -p 2222' |
--bwlimit=10m |
限速 10MB/s | 备份必备 |
--checksum |
按校验和判断差异 | 慢但准,默认按大小+时间 |
--size-only |
只比大小 | 快,可能漏 |
--inplace |
直接写目标文件 | 省空间,非原子 |
--partial |
保留中断的临时文件 | 大文件必备 |
--append |
追加模式 | 只适合只增日志 |
--link-dest=DIR |
硬链接未变化文件 | 增量备份省空间 |
--numeric-ids |
不映射用户/组名 | 跨系统迁移用 |
--chown=user:group |
强制属主 | |
-H |
保留硬链接 | |
-A / -X |
保留 ACL / xattr | 需目标 FS 支持 |
--remove-source-files |
传完删源 | 搬运场景 |
--max-delete=N |
最多删 N 个 | 防误删护栏 |
--timeout=60 |
IO 超时 | 防挂死 |
--stats |
传输统计 | |
--log-file=FILE |
日志 |
5. 远程同步(走 SSH)
# 推送到远程
rsync -avz -e 'ssh -p 2222' /data/ user@10.0.0.5:/backup/data/
# 从远程拉
rsync -avz user@10.0.0.5:/backup/data/ /data/
# 用密钥 + 指定配置
rsync -avz -e 'ssh -i ~/.ssh/id_ed25519 -o StrictHostKeyChecking=no' ...
免密是前提,否则 cron 任务会卡在密码提示。先在两台机器间配好 ssh-keygen + ssh-copy-id。
rsync daemon 模式(873 端口,适合大批机器):
# 服务端 /etc/rsyncd.conf
cat > /etc/rsyncd.conf <<'EOF'
uid = root
gid = root
use chroot = yes
max connections = 20
[backup]
path = /data/backup
read
auth users = bkuser
secrets file = /etc/rsyncd.secrets
EOF
echo 'bkuser:StrongPass123' > /etc/rsyncd.secrets
chmod 600 /etc/rsyncd.secrets
systemctl enable --now rsyncd
# 客户端
rsync -avz --password-file=/etc/rsync.pass bkuser@10.0.0.5::backup/ /local/
daemon 模式明文传输,跨公网必须套 VPN 或 SSH 隧道。
6. 排除规则怎么写
rsync -av --exclude='*.log' --exclude='cache/' --exclude='.git' /data/ /backup/
rsync -av --exclude-from=/etc/rsync-exclude.txt /data/ /backup/
/etc/rsync-exclude.txt:
*.tmp
*.log
cache/
node_modules/
.git/
/data/tmp/
规则要点:
- 以
/开头表示相对传输根;不以/开头匹配任意层级。 - 以
/结尾只匹配目录。 *不跨/,**跨目录。--include与--exclude按出现顺序生效,先匹配先生效。
只同步某几类文件:
rsync -av --include='*/' --include='*.jpg' --exclude='*' /photos/ /backup/
# 注意必须先 include 目录,否则进不去
7. 实战场景
7.1 首次迁移服务器(保留一切属性)
# 源端执行,先试运行
rsync -avnHAX --numeric-ids --exclude={/proc,/sys,/dev,/tmp,/run,/var/cache} \
/ root@newhost:/
# 确认清单没问题后去掉 -n 正式跑
注意:/proc、/sys、/dev、/run 绝对不能同步;正在写入的数据库文件要停库或用快照。
7.2 增量备份 + 硬链接省空间
DEST=/backup/$(date +%F)
rsync -av --delete --link-dest=/backup/latest /data/ "$DEST/"
rm -f /backup/latest && ln -s "$DEST" /backup/latest
每天的备份目录里,没变的文件是硬链接,只有变化部分占新空间。几十天备份可能只占 1.2 倍空间。
7.3 限速备份,不影响业务
rsync -avz --bwlimit=20m --timeout=300 /data/ /backup/data/
--bwlimit 单位默认 KB/s,带 m 后缀是 MB/s。
7.4 断点续传大文件
rsync -avP --partial --append-verify bigfile.iso user@host:/data/
--append-verify 会在追加后校验,比 --append 安全。
7.5 只删目标端多余文件(不传新文件)
rsync -avn --delete /data/ /backup/data/ # 先看会删什么
rsync -av --delete --existing /data/ /backup/data/ # --existing 只更新已存在文件
7.6 同步大量小文件
rsync -av --no-compress --whole-file -e 'ssh -T -c aes128-gcm@openssh.com -o Compression=no' \
/data/many-files/ user@host:/data/
小文件瓶颈在元数据与 SSH 加密开销,关压缩、用快加密算法能明显提速。文件超过十万,考虑先 tar 再传。
8. 危险操作与护栏
| 危险 | 后果 | 护栏 |
|---|---|---|
--delete 源目写反 |
把备份端的旧数据同步到源端,源端被删空 | 永远先 -n;加 --max-delete=100 |
/data 与 /data/ 混淆 |
目标下多一层或内容铺平 | 先 -n 看输出路径 |
同步 / 到已运行机器 |
覆盖系统文件致无法启动 | 排除 /proc /sys /dev /boot |
| 同步数据库数据目录 | 文件不一致,库损坏 | 停库、FLUSH TABLES WITH READ LOCK 或快照 |
--remove-source-files 配错目标 |
源被删但目标没写成 | 先 -n,--remove-source-files 只删传输成功的文件,仍要谨慎 |
通用安全模板:
rsync -avn --delete --max-delete=100 --exclude-from=exclude.txt SRC/ DST/ | tee /tmp/plan.txt
# 人工确认 plan.txt 里没有意外的 "deleting"
9. 常见坑
- 尾部斜杠语义(重复强调):
srcvssrc/结果不同。 - 默认按"大小 + mtime"判断差异:时钟不同步或 mtime 被改会导致漏传,用
--checksum强制。 --delete与--exclude交互:被排除的文件默认不会在目标端删除;要删需--delete-excluded。-a不含 ACL 与 xattr:需要-A -X,且目标文件系统要支持。- 根用户同步普通用户文件会改属主:跨系统用
--numeric-ids或--chown。 -z对已压缩文件无效:jpg/zip/mp4 再压缩只浪费 CPU。--inplace不是原子操作:中途失败会留下半个文件,不适合关键数据。--append只判断大小,不校验内容:源文件被改写会导致数据错位,用--append-verify。- SELinux 环境丢失上下文:加
-X或在目标端restorecon -R。 - cron 里跑 rsync 找不到密钥:cron 环境无
SSH_AUTH_SOCK,用-i指定私钥并确保权限 600。 - 跨文件系统
-H硬链接可能失效,且大量硬链接会拖慢。 rsync不处理正在打开的文件:日志类文件建议先flush或用--ignore-existing。
10. 速查表
rsync -avn SRC/ DST/ # 试运行(第一步永远是它)
rsync -av SRC/ DST/ # 本地同步
rsync -avz SRC/ user@host:DST/ # 远程推送
rsync -avz user@host:SRC/ DST/ # 远程拉取
rsync -avz -e 'ssh -p 2222' SRC/ host:DST/ # 非标端口
rsync -avP --partial SRC/ DST/ # 断点续传
rsync -av --delete --max-delete=100 SRC/ DST/ # 镜像(带护栏)
rsync -av --exclude-from=ex.txt SRC/ DST/ # 排除规则
rsync -av --bwlimit=20m SRC/ DST/ # 限速
rsync -av --link-dest=/backup/latest SRC/ /backup/$(date +%F)/ # 增量备份
rsync -av --checksum SRC/ DST/ # 按校验和
rsync -av --stats SRC/ DST/ # 统计