Лучший способ синхронизации файлов - копировать только СУЩЕСТВУЮЩИЕ файлы и только если НОВИНКА, чем цель

18

Я делаю эту синхронизацию локально на Ubuntu 12.04. Файлы, как правило, представляют собой небольшие текстовые файлы (код).

Я хочу скопировать (сохраняя метку mtime) из sourceкаталога в, targetно я хочу копировать, только если файл target уже существует и старше, чем файл в source.

Так что я копирую только те файлы, которые новее source, но они должны существовать, targetиначе они не будут скопированы. ( sourceбудет иметь гораздо больше файлов, чем target.)

Я на самом деле буду копировать из sourceнескольких targetкаталогов. Я упоминаю об этом на случай, если это повлияет на выбор решения. Тем не менее, я могу легко запустить мою команду несколько раз, указав новую targetкаждый раз, если это то, что требуется.

MountainX для Моники Челлио
источник

Ответы:

29

Я считаю, что вы можете использовать rsyncдля этого. Наблюдение ключ будет в необходимости использовать --existingи --updateпереключатели.

        --existing              skip creating new files on receiver
        -u, --update            skip files that are newer on the receiver

Такая команда сделает это:

$ rsync -avz --update --existing src/ dst

пример

Скажем, у нас есть следующие образцы данных.

$ mkdir -p src/; touch src/file{1..3}
$ mkdir -p dst/; touch dst/file{2..3}
$ touch -d 20120101 src/file2

Который выглядит следующим образом:

$ ls -l src/ dst/
dst/:
total 0
-rw-rw-r--. 1 saml saml 0 Feb 27 01:00 file2
-rw-rw-r--. 1 saml saml 0 Feb 27 01:00 file3

src/:
total 0
-rw-rw-r--. 1 saml saml 0 Feb 27 01:00 file1
-rw-rw-r--. 1 saml saml 0 Jan  1  2012 file2
-rw-rw-r--. 1 saml saml 0 Feb 27 01:00 file3

Теперь, если бы я синхронизировал эти каталоги, ничего бы не случилось:

$ rsync -avz --update --existing src/ dst
sending incremental file list

sent 12 bytes  received 31 bytes  406.00 bytes/sec
total size is 0  speedup is 0.00

Если мы touchисходный файл, чтобы он был новее:

$ touch src/file3 
$ ls -l src/file3
-rw-rw-r--. 1 saml saml 0 Feb 27 01:04 src/file3

Еще один прогон rsyncкоманды:

$ rsync -avz --update --existing src/ dst
sending incremental file list
file3

sent 115 bytes  received 31 bytes  292.00 bytes/sec
total size is 0  speedup is 0.00

Мы можем видеть, что file3, поскольку он более новый и существует dst/, он отправляется.

тестирование

Для того, чтобы убедиться , что все работает , прежде чем вырезать команду свободно, я предлагаю использовать другие rsyncкоммутаторы «S, --dry-run. Давайте добавим еще один, -vчтобы rsyncрезультат был более подробным.

$ rsync -avvz --dry-run --update --existing src/ dst 
sending incremental file list
delta-transmission disabled for local transfer or --whole-file
file1
file2 is uptodate
file3 is newer
total: matches=0  hash_hits=0  false_alarms=0 data=0

sent 88 bytes  received 21 bytes  218.00 bytes/sec
total size is 0  speedup is 0.00 (DRY RUN)
SLM
источник
Спасибо. Разве мне не нужно больше опций rsync? Я читаю справочную страницу. Кажется , что я , возможно , это нужно: rsync --archive --update --existing --whole-file --itemize-changes a/ b. Или большинство из этих вариантов не нужны? (Я добавил весь файл, потому что это в основном небольшие текстовые файлы.)
MountainX для Monica Cellio
@MountainX - добавляйте только те опции, которые вам нужны. Я бы начал с -aтого, что это супер-набор переключателей -rlptgoD.
SLM
Позвольте мне уточнить это. Я запутался о --updateи --existing. Нужны ли мне оба? Я проверил ваше решение, и оно, кажется, работает, но я все еще чувствую себя безопаснее, добавляя --update.
MountainX для Моники Челлио
@MountainX - конечно, вы можете добавить его, я тоже положу его в А.
SLM