Рекурсивно добавлять файлы по шаблону
Как я могу рекурсивно добавлять файлы по шаблону (или глобусу), расположенному в разных каталогах?
Например, я хотел бы добавить A/B/C/foo.java
и D/E/F/bar.java
(и несколько других java файлов) с помощью одной команды:
git add '*.java'
К сожалению, это не работает должным образом.
Ответы
Ответ 1
Ответ Sergio Acosta, вероятно, лучше всего, если некоторые из файлов, которые нужно добавить, могут не отслеживаться. Если вы хотите ограничить себя файлами, которые git уже знает, вы можете объединить git-ls-files
с фильтром:
git ls-files [path] | grep '\.java$' | xargs git add
Git не предоставляет каких-либо причудливых механизмов для этого, поскольку это в основном проблема оболочки: как вы получаете список файлов для предоставления в качестве аргументов данной команды.
Ответ 2
Вы можете использовать git add [path]/\*.java
для добавления файлов java из подкаталогов,
например, git add./\*.java
для текущего каталога.
Из git add
документацию:
Добавляет содержимое из всех файлов *.txt
каталоге Documentation
и его подкаталогах:
$ git add Documentation/\*.txt
Обратите внимание, что звездочка *
указана в командной строке в этом примере; это позволяет команде включать файлы из подкаталогов каталога Documentation/
.
Ответ 3
Отключить тему (не конкретно git), но если вы используете linux/unix, это может быть:
find . -name '*.java' | xargs git add
И если вы ожидаете пути с пробелами:
find . -name '*.java' -print0 | xargs -0 git add
Но я знаю, что это не совсем то, что вы просили.
Ответ 4
С помощью zsh
вы можете запустить:
git add "**/*.java"
и все ваши файлы *.java
будут добавлены рекурсивно.
Ответ 5
Ответ Сергея (не кредитуйте меня) работает:
You can use git add [path]/\*.java
с недавним git:
$git version
git version 1.7.3.4
Файлы для теста:
$find -name .git -prune -o -type f -print | sort
./dirA/dirA-1/dirA-1-1/file1.txt
./dirA/dirA-1/dirA-1-2/file2.html
./dirA/dirA-1/dirA-1-2/file3.txt
./dirA/dirA-1/file4.txt
./dirB/dirB-1/dirB-1-1/file5.html
./dirB/dirB-1/dirB-1-1/file6.txt
./file7.txt
Git статус:
$git status -s
?? dirA/
?? dirB/
?? file7.txt
Добавление *.txt:
$git add \*.txt
Обновлен статус:
$git status -s
A dirA/dirA-1/dirA-1-1/file1.txt
A dirA/dirA-1/dirA-1-2/file3.txt
A dirA/dirA-1/file4.txt
A dirB/dirB-1/dirB-1-1/file6.txt
A file7.txt
?? dirA/dirA-1/dirA-1-2/file2.html
?? dirB/dirB-1/dirB-1-1/file5.html
Ответ 6
Если вы уже отслеживаете свои файлы и внесли в них изменения, и теперь вы хотите добавить их выборочно на основе шаблона, вы можете использовать флаг --modified
git ls-files --modified | grep '<pattern>' | xargs git add
Например, если вы хотите только добавить изменения CSS в этот фиксатор, вы можете сделать
git ls-files --modified | grep '\.css$' | xargs git add
См. man git-ls-files
для большего количества флагов
Ответ 7
Я хотел только добавить файлы с определенной строкой на основе git status
:
git status | grep string | xargs git add
а затем удалось git commit -m 'commit msg
передать все измененные файлы с помощью "string" в заголовке файла
Ответ 8
Просто используйте git add *\*.java
. Это добавит все .java файлы в корневой каталог и все подкаталоги.
Ответ 9
Как упоминалось в "git: как я рекурсивно добавляю все файлы в поддереве каталога, которые соответствуют шаблону glob?", если вы правильно убегаете или цитируете (например, '*.java'
), затем да, git добавить '*.java'
Git 2.13 (Q2 2017) улучшает это для интерактивного добавления:
См. commit 7288e12 (14 марта 2017 г.) Джефф Кинг (peff
).
(слияние Junio C Hamano - gitster
- в совершить 153e0d7, 17 марта 2017 г.
add --interactive
: не расширяйте pathspecs с помощью ls-files
Когда мы хотим получить список модифицированных файлов, мы сначала расширим любые предоставленные пользователем пути с помощью "ls-files
", а затем передаем результирующий список путей в качестве аргументов "diff-index
" и "diff-files
".
Если ваш pathspec расширяется на большое количество путей, вы можете столкнуться с одной из двух проблем:
-
ОС может жаловаться на размер аргумента список и отказаться от запуска. Например:
$ (ulimit -s 128 && git add -p drivers)
Can't exec "git": Argument list too long at .../git-add--interactive line 177.
Died at .../git-add--interactive line 177.
Это в репозитории linux.git
, который содержит около 20K файлов в каталоге "drivers" (ни один из них не был изменен в этом случае). Трюк "ulimit -s
" необходим, чтобы показать проблему в Linux даже для такого гигантского набора путей.
Другие операционные системы имеют гораздо меньшие пределы (например, реальный случай был замечен только с 5K файлами в OS X).
-
Даже когда он работает, он очень медленный. Путь код не оптимизирован для огромного количества путей. Вот в том же случае без ulimit:
$ time git add -p drivers
No changes.
real 0m16.559s
user 0m53.140s
sys 0m0.220s
Мы можем улучшить это, полностью пропустив "ls-files
" и просто загрузив исходные пути к командам diff.
Исторически язык pathspec, поддерживаемый "diff-index
", был слабее, но это уже не так.
Ответ 10
Добавление решения для командной строки Windows, которое еще не было упомянуто:
for /f "delims=" %G in ('dir /b/s *.java') do @git add %G
Ответ 11
поместите строку в ~/.gitconfig
[alias] addt = !sh -c 'git ls-files | grep \"\\.$1*\" | xargs git add' -
Если вы хотите добавить все измененные файлы Java, просто сделайте: git addt java
Точно так же, если вы хотите добавить все измененные файлы Python, просто сделайте: git addt py