Как можно синхронизировать набор подкаталогов с помощью rsync?

Как можно синхронизировать набор подкаталогов с помощью rsync?

У меня есть исходный каталог, который выглядит следующим образом (с многочисленными подкаталогами внутри каталогов src и bin):

  • топ_дир
    • проект1
      • источник/
      • мусорное ведро/
      • скрипты/
      • какой-тофайл.txt
    • проект2
      • источник/
      • мусорное ведро/
      • цель
        • мусорное ведро/
      • файл.xml

Я хотел бы синхронизировать с помощью rsync только каталоги bin, находящиеся непосредственно в каталогах проекта (т. е. игнорировать top_dir/proj2/target/bin/), и их содержимое в целевой каталог, чтобы это выглядело так:

  • топ_дир
    • проект1
      • мусорное ведро
    • проект2
      • мусорное ведро

Вероятно, я мог бы заставить это работать, явно перечислив каждый каталог bin (в моем реальном сценарии их около 15) в файле include-from, но я подумал, что должен быть способ указать, что я хочу синхронизировать все каталоги top_dir/*/bin.

решение1

Возможность 1

Используя расширение оболочки 1 вместо rsyncправил фильтрации, вы можете сделать следующее:

а. Чтобы включить все binкаталоги в top_dirиерархию:

rsync -av -R top_dir/**/bin/ destination_path

Вот параметр -Rrsync 2 , обозначающийродственник. man rsyncобъясняет это как

Используйте относительные пути. Это означает, что на сервер отправляются полные имена путей, указанные в командной строке, а не только последние части имен файлов. Это особенно полезно, когда вы хотите отправить несколько разных каталогов одновременно.

но по сути это означает, что структура каталогов сохраняется.

**является шаблоном подстановки оболочки и рекурсивно ищет каталоги, названные binв top_dir. Таким образом, в приведенном выше примере командная строка расширяется до:

rsync -av -R top_dir/proj1/bin/ top_dir/proj2/bin/ destination_path

б. Если вы хотите включить только binкаталоги, находящиеся на один уровень ниже каталога проекта, просто используйте один *(это работает и со «старыми» оболочками!):

rsync -av -R top_dir/*/bin/ destination_path

1 Вам нужен недавнийБашверсии (>4) и активировать рекурсивную подстановку через shopts -s globstar. СзшПо умолчанию используется рекурсивная подстановка.

2 rsync версии v3.2.3 протокола версии 31 на Linux.

Возможность 2

Только используя правила фильтрации rsync, вам нужно:

а. Чтобы включить все binкаталоги в top_dirиерархию:

rsync -av -m --include='**/' --include='**/bin/**' --exclude='*' top_dir/ destination_path

Первое includeправило может быть неочевидным 3 , но оно гарантирует, что будут прочитаны все каталоги (обратите внимание на завершающий символ /), второе добавляет все в binкаталоги, а excludeправило исключает все остальное. -mОно гарантирует, что пустые каталоги не будут скопированы.

б) Чтобы включить только один уровень ниже каталога проекта:

rsync -av -m  --include='/*/' --include='/*/bin/***' --exclude='*' top_dir/ destination_path

Использование ***синтаксиса rsync >= 2.6.7. Ведущие символы /в шаблонах представляют top_dir, в противном случае шаблоны сопоставляются сконецпути к файлу.


3 Поиск /some/path/this-file-will-not-be-foundвman rsync

решение2

Вы можете исключить все srcкаталоги, используя--exclude src/

Связанный контент