Linux rsync 命令:目录同步、预演与删除风险检查

rsync 用于在本地目录之间或本地与远程主机之间同步文件,默认根据大小和修改时间判断哪些文件需要更新。先用 --dry-run 核对源、目标和预计变化,再执行复制;尤其要分清源目录末尾的斜杠和 --delete 的删除范围。

反复传输大文件时,rsync 可用差异传输减少网络数据量,但并非每次都只传改动的字节。两端都是本地路径时,默认通常整文件传送;文件选择、数据传送方式和备份版本保留是三件不同的事。

基本语法与准备条件

rsync [options] source destination

source 是源,destination 是目标。先用 rsync --version 和 man rsync 确认本机版本与选项;远程复制也要检查远端安装版本。不要把另一工具的参数或路径规则直接套用。

确认源存在且可读,目标可写且有足够空间,父目录已准备好,源与目标没有意外重叠。示例 project、source、backup 是练习路径,alice 和 server.example.com 也须换成已获授权的真实账号和服务器。

-a 是归档模式,通常等价于 -rlptgoD,结合递归、符号链接及部分属性保留;实际所有者、组、权限和特殊文件的处理仍受权限与文件系统支持限制。它不会自动保留 ACL(访问控制列表)、扩展属性、硬链接关系或所有时间字段。

先预览,再同步本地或远程目录

预览本地复制。先准备可丢弃的 project/ 测试目录与 backup/ 父目录,并放入一个自建文件;使用下面的命令检查目标层级与预计更新:

rsync -av --dry-run project/ backup/project/

源 project/ 的末尾斜杠表示复制其内容,预期进入 backup/project/。预览不写入目标文件;要更清楚地列出属性变化,可在同一命令加 -i。预览并不保证正式运行时仍有相同内容、权限和容量。

执行本地同步。确认预览符合预期后,仅去掉 --dry-run:

rsync -av project/ backup/project/

新文件会复制,需要更新的目标文件可能被覆盖;这里没有 --delete,因此不会仅因源中缺少同名项就删除目标多余文件。重新执行时,大小和修改时间相同的数据通常跳过,指定的属性仍可能被调整。

通过 SSH 推送到远程。在已确认账号、主机身份、目标路径和权限后使用:

rsync -av project/ alice@server.example.com:/home/alice/project/

此写法把本地 project/ 内容推送到远端指定目录。单冒号使用远程 shell,通常是 SSH,但 -e 或环境配置可以改变传输程序;要明确选择 SSH 与端口,可加 -e 'ssh -p 2222'。两端都需要 rsync,远端不必专门运行 rsync 守护进程。

SSH 登录检查见 SSH 主机指纹、账号与端口核对。双冒号 host::module 或 rsync:// 则属于守护进程访问方式,不应因为工具名相同就认定连接已经用 SSH 加密。

怎样理解预览与目录末尾斜杠

假设 source/ 中有 notes.txt,而 backup/ 中还没有这个文件,先预览:

rsync -av --dry-run source/ backup/

输出可能包含下面的片段,实际列表还会随版本、目录和属性状态变化:

sending incremental file list
notes.txt

这表示计划把 notes.txt 放入 backup/,不是已经完成复制。若把源改成 source,在预先存在的 backup/ 目录下通常得到 backup/source/notes.txt;源为 source/ 则通常得到 backup/notes.txt。目标是否存在及复制项目数量也会影响命名,不能只看目标末尾有没有斜杠。

源路径的斜杠并不意味着源目录属性完全不参与处理。应同时检查文件内容、目录层级和属性,先用专用测试目录验证布局。-a 默认保留符号链接本身,若另加改变链接处理的选项,复制范围可能变化。

常用选项及其边界

选项 作用与条件
-a 递归并保留多项属性,不等于保存所有元数据。
-v 显示较详细的处理信息,不能代替退出状态和内容检查。
-n, --dry-run 预演变化,不实际复制或删除目标数据。
--delete 清理同步目录范围内目标独有的项目,先核对删除计划。
--exclude=pattern 按规则排除传输项目;一般排除规则也保护目标对应项免于删除。
-e 'ssh -p port' 指定远程 shell 和 SSH 端口,将 port 换成真实端口号。

例如排除 --exclude='*.tmp' 时,引号防止本地 shell 先展开通配符。规则基于传输路径和匹配位置,复杂过滤应先用实际目录预演。加入 --delete-excluded 或仅作用于发送端的规则,会改变排除项的删除保护,不能沿用原来的判断。

需要按内容重新判断是否传送时可考虑 -c,但它会读取两端文件计算校验值,增加磁盘开销。该传输前比较与正常传输期间用于验证重建数据的校验不是同一步,也不能代替可信备份与实际恢复测试。

删除、备份与执行后的检查顺序

  1. 确认路径、挂载点和源文件可用,记录现有重要目标文件,准备独立备份。在持续写入的数据库等场景,先使用应用支持的一致性备份或快照方案。
  2. 使用最终所需的完整选项加 --dry-run 预览。若计划使用 --delete,预览也必须包含它;核对每个待删除路径与过滤规则后再执行。
  3. 正式运行后立即查看退出状态,例如紧接执行 echo $?。0 表示成功;23 代表因错误发生部分传输,24 代表源文件消失导致部分传输,应结合错误信息检查而非当作全部完成。
  4. 核对目标布局、文件数量和大小,重要文件比较摘要并实际读取或恢复。失败后先保留诊断与已有备份,重新评估源和目标,再重试;不要把新旧混合目录直接当作一致快照。

--delete 只在同步的目录范围内处理目标多余项;用 shell 展开的 source/* 与直接传整个 source/ 并不等价。默认的发送端 I/O 错误保护也不能替代备份,不应为消除报错随意加 --ignore-errors。

镜像会传播源端误改、损坏以及启用删除时的缺失,不会自动保留历史版本。应另行设计版本保留、独立副本、失败告警和恢复演练;同步成功与能够恢复到需要的时间点是不同标准。

常见问题

source 和 source/ 到底怎样选择?

想把内容直接放到目标目录时用 source/;想在已有目标目录下包含 source 这一层时通常用 source。先确认目标存在状态,并预览完整路径,避免层级错误后又用删除选项修补。

官方文档

选项、路径、过滤与退出状态参见 rsync 项目官方手册。本机安装版本与编译支持可能不同,应结合本机手册判断可用行为。