Can rsync handle moves and renames?
Suppose I have a directory structure like
├── src
│ ├── folder_a
│ │ ├── file_w
│ │ └── file_x
│ ├── folder_b
│ │ ├── file_y
│ │ └── file_z
and I back it up using rsync
:
$ rsync -r /path/to/src/ /path/to/dst/
Later, I reorganize the contents of src
, for example:
├── src
│ ├── folder_c
│ │ ├── file_w
│ │ └── file_y
│ ├── folder_d
│ │ ├── file_x
│ │ └── file_z
Each file with a given name has not changed; but they don't have the same hierarchical relationship (i.e., files that used to be siblings might not be any more), and the names of their containing folders may have changed.
Can rsync
detect that the dst
folder contains the same files, and avoid copying files (instead only moving files within dst
and renaming folders)? What options are useful to make this as smooth as possible?
1 answer
I'm quite certain that rsync is not able to deduce that /path/to/src/folder_a/file_w on one side of the transfer is identical to /path/to/src/folder_c/file_w on the other side of the transfer.
Therefore, rsync won't be able to handle such a move efficiently. To stock rsync, it will appear as one file having been deleted and the other having been created.
There are basically two ways of handling this:
- Independently make the same changes on both sides of the transfer. That's easy for a single file, or if you control both sides and can access them simultaneously; but that might not always be practical.
- Use a tool better suited for such change detection.
For example, if the (in this case) source code is in a Git repository, you can use git mv
to rename the parent directory; this should allow the tooling to keep track of which file is which even after the rename. Other version control systems will likely have ways to do much the same thing.
Alternatively, you can use a tool such as unison, possibly in one-way mode, to synchronize changes. I can attest to that it generally successfully detects and handles renames without re-transferring the file, but it relies on a fairly hefty chunk of external metadata to do so efficiently, and generally wants to either do the initial transfer itself or start with two identical trees; using it to transfer such a change after it has already been made would probably be risky.
0 comment threads