2013-07-01 1 views
3

Я пытаюсь написать правило .gitignore, чтобы исключить некоторые файлы в определенном каталоге с несколькими уровнями подкаталогов.Почему шаблон glob с двойной звездочкой не соответствует чему-либо в подкаталогах?

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

out 
├─a 
│ ├─source 
│ │ ├─.keepme 
│ │ ├─183597.txt 
│ │ ├─271129.txt 
│ │ └─288833.txt 
│ └─parsed 
│ ├─.keepme 
│ ├─183597.csv 
│ ├─271129.csv 
│ └─288833.csv 
├─b 
│ └─(...) 

(etc.) 

Я хотел бы сохранить .keepme файлов (так что Git сохраняет структуру каталогов), так что я полагаю, что я буду писать правила, чтобы соответствовать что-нибудь под out, что соответствует шаблону ?*.*:

out/**/?*.* 

Однако это не соответствует файлов.

Я думал, что ** будет соответствовать любому количеству подкаталогов; почему это не работает?

Я запускаю Git 1.8 в Bash 4.2 на Fedora 18 VM.

+0

Из любопытства, почему вы хотите создать структуру каталогов без каких-либо файлов? –

+1

Что бы вы могли сделать, если вы знаете, что никогда не захотите добавить больше файлов из 'out' в git, просто добавить файлы' .keepme' в индекс git, зафиксировать их, а затем добавить ' out/'to' .gitignore'. Файлы '.keepme' будут версироваться до тех пор, пока они останутся в репозитории, но новые файлы под' out/'не будут добавлены. –

+0

@EmilLundberg Хороший вопрос. Эти каталоги будут хранить выходные файлы, и в этом случае проще включить структуру каталогов в репозиторий, чем проверить программу на наличие файлов перед сохранением вывода. –

ответ

6

Во-первых, убедитесь, что вы используете Git 1.8.2 или выше, так как именно тогда появилась поддержка **.

Похоже, вы пытаетесь исключить файлы .keepme, сопоставив *.*. Однако, поскольку * соответствует нулю или больше символов, он соответствует пустой строке перед периодом в .keepme, включая этот файл.

Может быть, вы хотели, чтобы работать как out/**/?*.*

Если вы хотите, чтобы соответствовать всем не-точечным файлам, вы можете использовать out/**/[!.]*, который также будет включать в себя имена файлов без периодов в них, как Makefile.

+2

Или 'out /**/[!.]*.*', который будет соответствовать всем, что содержит период и не начинается с периода. –

+0

Это хорошее наблюдение, спасибо! Я обновлю свой вопрос, чтобы удалить двусмысленность (часть, которая меня действительно интересует, поэтому часть '**' не работает так, как я ее ожидал). –

0

Я думаю, что ответ другого парня - хорошее преимущество. Шаблон out/**/[!.]*.*, который должен соответствовать всем, что содержит период и не начинается с периода, также работает в моем тесте в Баш, Arch Linux:

$ find * -type f 
out/a/source/4232352.txt 
out/a/source/1312312.txt 
out/a/source/4234234.txt 
out/a/source/.keepme 
out/a/parsed/1231222.csv 
out/a/parsed/9593343.csv 
out/a/parsed/5675675.csv 
out/a/parsed/.keepme 
$ cat .gitignore 
out/**/[!.]*.* 

$ git init && git add -A && git status --ignored 
# On branch master 
# 
# Initial commit 
# 
# Changes to be committed: 
# (use "git rm --cached <file>..." to unstage) 
# 
# new file: .gitignore 
# new file: out/a/parsed/.keepme 
# new file: out/a/source/.keepme 
# 
# Ignored files: 
# (use "git add -f <file>..." to include in what will be committed) 
# 
# out/a/parsed/1231222.csv 
# out/a/parsed/5675675.csv 
# out/a/parsed/9593343.csv 
# out/a/source/1312312.txt 
# out/a/source/4232352.txt 
# out/a/source/4234234.txt 

EDIT: Кажется, это на самом деле не работает в git bash в комплекте с версией git для Windows, ни один из вышеперечисленных файлов не игнорируется этим .gitignore.

+0

Очень интересно. Какую ОС/оболочку вы используете? Кажется, он не работает в моей системе (результат в том, что ничего не игнорируется). Я также добавлю свои спецификации к вопросу. –

+1

Arch Linux, bash. В данный момент у меня нет компьютера на моей стороне, но я мог бы вернуться к вам позже с дополнительной информацией, если это необходимо. –

+1

Да, похоже, это не работает в git Bash в комплекте с git в Windows ... –

 Смежные вопросы

  • Нет связанных вопросов^_^