список всех файлов, имеющих набор атрибутов git

git check-attr позволяет мне проверить, установлен ли атрибут в .gitattributes для определенного набора файлов. е.г:

# git check-attr myAttr -- org/example/file1 org/example/file2
org/example/file1: myAttr: set
org/example/file2: myAttr: unspecified

есть ли простой способ перечислить все файлы, имеющие myAttr установить, включая все подстановочные знаки?

3 ответов


вы можете установить в качестве аргумента список со всеми файлами в вашем репозитории, используя git ls-files, например:

git check-attr myAttr `git ls-files`

если в вашем репозитории слишком много файлов, вы можете получить следующую ошибку:

- bash:/usr/bin / git: список аргументов слишком длинный

что вы можете преодолеть с xargs:

git ls-files | xargs git check-attr myAttr

наконец, если у вас слишком много файлов, вы, вероятно, хотите, чтобы отфильтровать те, где вы не указали аргумент, чтобы сделать вывод более читаемым:

git ls-files | xargs git check-attr myAttr | grep -v 'unspecified$'

С grep вы можете применить больше фильтров к этому выходу, чтобы соответствовать только файлам, которые вы хотите.


если вы хотите получить только список файлов и использовать символ NUL для устойчивости к именам файлов или атрибутам, которые содержат \n или :, вы можете сделать:

для списка файлов, имеющих атрибут "merge=union":

git ls-files -z | git check-attr --stdin -z merge | sed -z -n -f script.sed

со скриптом.sed:

             # read filename
x            # save filename in temporary space
n            # read attribute name and discard it
n            # read attribute name
s/^union$//  # check if the value of the attribute match
t print      # in that case goto print
b            # otherwise goto the end
:print
x            # restore filename from temporary space
p            # print filename
             # start again

то же самое с встроенным скриптом sed (т. е. с использованием -e вместо -f, игнорируя комментарии и заменяя новые строки точкой с запятой):

git ls-tree -z | git check-attr --stdin -z merge | sed -zne 'x;n;n;s/^union$//;t print;b;:print;x;p'

PS: результат разделяет имена файлов с помощью символа NUL, используйте | xargs --null printf "%s\n" для того, чтобы печатать их в удобочитаемое пути.


другие сообщения не работали хорошо для меня, но я добрался туда:

git ls-files | git check-attr -a --stdin

"проверить каждый файл в Git и распечатать все фильтры" один лайнер.