Rsync включает отличную возможность --cvs-exclude
«игнорировать файлы так же, как это делает CVS», но CVS уже много лет устарела. Есть ли способ сделать так, чтобы он также исключал файлы, которые игнорировались бы современными системами контроля версий (Git, Mercurial, Subversion)?
Например, у меня есть много проектов Maven, проверенных на GitHub. Обычно они включают в себя .gitignore
список как минимум target
каталога сборки Maven по умолчанию (который может присутствовать на верхнем уровне или в подмодулях). Поскольку содержимое этих каталогов полностью одноразовое и может быть намного больше исходного кода, я хотел бы исключить их при использовании rsync для резервного копирования.
Конечно, я могу явно, --exclude=target/
но это случайно подавит несвязанные каталоги, которые случайно названы target
и не должны игнорироваться.
И я мог бы предоставить полный перечень абсолютных путей для всех имен файлов и шаблонов , упомянутых в любом .gitignore
, .hgignore
или svn:ignore
собственность на моем диске, но это был бы огромный список , который должен был бы быть получен какой - то сценарий.
Поскольку rsync не имеет встроенной поддержки проверок VCS, кроме CVS, есть ли какой-нибудь хороший трюк, чтобы скормить ему их шаблоны игнорирования? Или какая-то система обратного вызова, с помощью которой пользовательский сценарий может быть задан вопрос, следует ли включать данный файл / каталог?
Обновление : --filter=':- .gitignore'
как было предложено LordJavac, похоже, работает также для Git, как --filter=:C
и для CVS, по крайней мере, в найденных мной примерах, хотя неясно, является ли синтаксис точным совпадением. --filter=':- .hgignore'
не очень хорошо работает для Mercurial; например, .hgignore
содержащий строку вроде ^target$
(Mercurial эквивалент Git /target/
) не распознается rsync как регулярное выражение. И, похоже, ничего не работает для Subversion, для которой вам придется разобрать .svn/dir-prop-base
рабочую копию 1.6 или более ранней версии и в ужасе вскинуть руки для рабочей копии 1.7 или более поздней версии.
:-
именно значит? Что означает двоеточие? Что за черта?check-ignore
подкоманду, которая может справиться с тяжелой работой по синтаксическому анализу различных «игнорируемых» файлов, если вы хотите использовать опцию «генерировать список всех не игнорируемых файлов». В моем ответе подробно описано, как это сделать.Ответы:
Как упоминал luksan, вы можете сделать это с помощью
--filter
переключателя наrsync
. Я добился этого с помощью--filter=':- .gitignore'
(есть пробел перед ".gitignore"), который сообщает,rsync
что нужно объединить каталог с.gitignore
файлами и исключить их по правилам git. Вы также можете добавить свой глобальный файл игнорирования, если он у вас есть. Чтобы упростить использование, я создал псевдоним, вrsync
который включен фильтр.источник
--exclude='/.git' --filter="dir-merge,- .gitignore"
rsync -rvv --exclude='.git*' --exclude='/rsync-to-dev.sh' --filter='dir-merge,-n /.gitignore' $DIR/ development.foobar.com:~/test/
.. но хотя там написано[sender] hiding file .gitignore because of pattern .git*
, файл все равно отправляется на удаление--delete
вариант, здесь работает из командной строки:rsync --delete-after --filter=":e- .gitignore" --filter "- .git/" -v -a ...
. Это заняло у меня некоторое время ...e
в фильтре, и--delete-after
оба они важны. Я предлагаю прочитать главу «ПРАВИЛА ДЛЯ КАТАЛОГА И УДАЛИТЬ» наrsync
странице руководства .--delete-after
удалений, добавлений и обновлений вы можете просто добавить в версию команды @ VasiliNovikov. (Это похоже на версию команды @ dboliton, за исключением того, что @db использует: e, что, как мне кажется, исключает копирование файлов .gitignore, а это не то, что я хотел.)Вы можете использовать
git ls-files
для построения списка файлов, исключенных из файлов репозитория.gitignore
. https://git-scm.com/docs/git-ls-filesПараметры:
--exclude-standard
Считайте все.gitignore
файлы.-o
Не игнорируйте неустановленные изменения.-i
Выводить только игнорируемые файлы.--directory
Выводить путь к каталогу, только если игнорируется весь каталог.Единственное, что я оставил игнорировать, это
.git
.источник
rsync -azP --exclude-from="$(git -C SRC ls-files --exclude-standard -oi --directory > /tmp/excludes; echo /tmp/excludes)" SRC DEST
.gitignore
!
--force
как насчет
rsync --exclude-from='path/.gitignore' --exclude-from='path/myignore.txt' source destination
?У меня это сработало.
Я считаю, что у вас тоже может быть больше
--exclude-from
параметров.источник
.gitignore
файлы используют синтаксис, совместимый сrsync
.Решение 2018 подтверждено
Подробности:
--exclude-from
обязательно вместо --exclude, потому что вероятный случай, когда список исключений не будет проанализирован как аргумент. Исключить из требует файла и не может работать с каналами.Текущее решение сохраняет файл исключений внутри папки .git, чтобы гарантировать, что он не повлияет
git status
, сохраняя его автономным. Если хотите, можете использовать / tmp.источник
SRC
здесь, - но не для исходной проблемы, о которой я говорил, которая представляет собой разрастающийся каталог с тысячами репозиториев Git в качестве подкаталогов на разной глубине, многие из которых имеют идиосинкразический.gitignore
s.--exclude-from=<(git -C SRC ls-files --exclude-standard -oi --directory)
Для ртутного вы можете использовать
собрать список файлов, которые НЕ находятся под постоянным контролем из-за ограничений .hgignore, а затем запустить
для rsync всех файлов, кроме игнорируемых. Обратите внимание на флаг -m в rsync, который исключит пустые каталоги из синхронизации, потому что hg status -i будет перечислять только исключенные файлы, а не каталоги
источник
Попробуй это:
rsync -azP --delete --filter=":- .gitignore" <SRC> <DEST>
Он может копировать все файлы в удаленный каталог, за исключением файлов в '.gitignore', и удалять файлы не в вашем текущем каталоге.
источник
На
rsync
странице руководства в дополнение к стандартному списку шаблонов файлов:Итак, мой файл $ HOME / .cvsignore выглядит так:
чтобы исключить .git и файлы, созданные Sass .
источник
.git/
каталоги, возможно, даже сильнее, чем рабочая копия. Я хочу исключить продукты сборки.rsync
странице руководства, цитируемое в этом ответе, описывает этот--cvs-exclude
параметр, поэтому вы должны использовать его явно. 2 / Вы можете создавать.cvsignore
файлы в любом каталоге, чтобы игнорировать специфичные для проекта файлы, они также читаются. 3 /.git
уже игнорируется при использовании--cvs-exclude
, согласно руководству, поэтому его использование$HOME/.cvsignore
кажется излишним.У меня было несколько очень больших
.gitignore
файлов, и ни одно из решений "чистого rsync" не помогло мне. Я написал этот сценарий оболочки rsync , он полностью соблюдает.gitignore
правила (включая!
исключения в стиле и.gitignore
файлы в подкаталогах) и работал для меня как шарм.источник
locate -0e .gitignore | (while read -d '' x; do process_git_ignore "$x"; done)
, но есть много проблем. Файлы в том же каталоге.gitignore
неправильно отделены от имени каталога с помощью/
. Пустые строки и комментарии неверно истолкованы. Давится.gitignore
файлами в путях с пробелами (не говоря уже о мерзавцах/opt/vagrant/embedded/gems/gems/rb-fsevent-0.9.4/spec/fixtures/custom 'path/.gitignore
изvagrant
пакета для Ubuntu). Возможно, лучше сделать это в виде Perl-скрипта.rsync
по той причине, что обработка кавычек / пробелов является такой болью. Если у вас есть пример сбойнойgsync
командной строки и.gitignore
связанные с ней файлы, я был бы рад изучить его поближе.rsync
целая файловая система с разбросанными по ней различными репозиториями Git. Возможно, ваш скрипт отлично подойдет для случая синхронизации одного репозитория.Ознакомьтесь с разделом ПРАВИЛА ФИЛЬТРА MERGE-FILES в rsync (1).
Похоже, что можно создать правило rsync --filter, которое будет включать файлы .gitignore по мере прохождения структуры каталогов.
источник
Вместо создания фильтров исключения вы можете использовать
git ls-files
для выбора каждого файла для rsync:Это работает, даже если
git ls-files
возвращает пути, разделенные новой строкой. Вероятно, не будет работать, если у вас есть версированные файлы с пробелами в именах файлов.источник
Альтернативы:
git ls-files -zi --exclude-standard |rsync -0 --exclude-from=- ...
git ls-files -zi --exclude-per-directory=".gitignore" |...
(rsync понимает только частично .gitignore)
источник
Короткий ответ
Значение параметров:
-r
: рекурсивный--info=...
: показать прогресс--filter=...
: исключить по правилам, указанным в файле .gitignoreисточник
После нескольких часов исследований я нашел именно то, что мне нужно: синхронизировать папку назначения с исходной папкой (также удаляя файлы в месте назначения, если они были удалены в источнике), а не копировать в место назначения файлы, которые игнорируются .gitignore, но также не удалять эти файлы в месте назначения :
Другими словами, эта команда полностью игнорирует файлы из .gitignore как в источнике, так и в месте назначения . Вы можете опустить
--exclude='/.git'
часть, если хотите скопировать и.git
папку.Вы ДОЛЖНЫ копировать файлы .gitignore из источника. Если вы будете использовать команду LordJavac, файл .gitignore не будет скопирован. И если вы создаете файл в папке назначения, который должен игнорироваться .gitignore, этот файл будет удален, несмотря на .gitignore. Это потому, что у вас нет файлов .gitignore в месте назначения. Но если у вас будут эти файлы, файлы, описанные в .gitignore, не будут удалены, они будут проигнорированы, как ожидается.
источник