Jak stwierdzić, czy plik jest śledzony przez git (według kodu wyjścia powłoki)?

357

Czy istnieje sposób, aby stwierdzić, czy plik jest śledzony, uruchamiając jakieś gitpolecenie i sprawdzając kod wyjścia?

Innymi słowy: czy git śledzi plik?

Dale Forester
źródło
Myślę, że chodzi o to, jakie są kryteria wyboru pliku jako śledzonego lub nieśledzonego. Do przeszukania powinna istnieć pewnego rodzaju kolekcja plików śledzonych.
smwikipedia

Odpowiedzi:

443

próbować:

git ls-files --error-unmatch <file name>

wyjdzie z 1, jeśli plik nie jest śledzony

hasen
źródło
Przynajmniej w mojej starszej (1.6.0) wersji git, musisz ustawić --error-unmatchopcję przed nazwą pliku, aby otrzymać błąd. Jakoś ta opcja jest stosowana tylko do nazw plików, które następują po niej.
Alex Dupuy,
W rzeczywistości problem polega na tym, że permutacja opcji GNU getopt nie jest włączona, a gdy pojawia się po nazwie pliku (lub po --), --error-unmatchjest traktowana jako kolejna nazwa pliku (nie w indeksie) i nie ma żadnego efektu.
Alex Dupuy,
29
git ls-files | grep <PATTERN>? przykład:git ls-files | grep Main.h
gaussblurinc
1
[Naiwny sposób] Dokonaj niewielkiej zmiany w pliku (dodaj / usuń spację). I sprawdź, czy plik jest wyświetlany na liście po wpisaniu „git status”. Głupi sposób, ale może zaoszczędzić czas.
BraveNinja
Ale dodałem go i zatwierdziłem poleceniem „git add -A && git commit -m" bla ". Nawet zobacz całe pliki za pomocą polecenia„ git ls-tree - only -name -r -r sha1 ".
Dr.jacky
66

Jeśli nie chcesz zaśmiecać konsoli komunikatami o błędach, możesz także uruchomić

git ls-files file_name

a następnie sprawdź wynik. Jeśli git nic nie zwraca, plik nie jest śledzony. Jeśli jest śledzone, git zwróci ścieżkę do pliku.

Jest to przydatne, jeśli chcesz połączyć to w skrypcie, na przykład PowerShell:

$gitResult = (git ls-files $_) | out-string
if ($gitResult.length -ne 0)
{
    ## do stuff with the tracked file
}
ser
źródło
Myślę, że file_namemusi być to dokładne dopasowanie (pełna ścieżka + nazwa pliku), ale można go używać z symbolami wieloznacznymi:git ls-files *foo.rb
dechimp
16

EDYTOWAĆ

Jeśli potrzebujesz użyć git z bash, istnieje --porcelainopcja git status:

--porcelana

Daj wynik w stabilnym, łatwym do przeanalizowania formacie dla skryptów. Obecnie jest to identyczne z wyjściem --short, ale gwarantuje, że nie zmieni się w przyszłości, dzięki czemu jest bezpieczne dla skryptów.

Dane wyjściowe wyglądają tak:

> git status --porcelain
 M starthudson.sh
?? bla

Lub jeśli robisz tylko jeden plik na raz:

> git status --porcelain bla
?? bla

ORYGINALNY

zrobić:

git status

Zobaczysz raport informujący, które pliki zostały zaktualizowane, a które nie są śledzone.

Możesz zobaczyć, że bla.shjest śledzony i modyfikowany i newblanie jest śledzony:

# On branch master
# Changed but not updated:
#   (use "git add <file>..." to update what will be committed)
#
#       modified:   bla.sh
#
# Untracked files:
#   (use "git add <file>..." to include in what will be committed)
#
#       newbla
no changes added to commit (use "git add" and/or "git commit -a")
stefanB
źródło
Przepraszam, że powinienem być jaśniejszy. Status jest w porządku, ale wolę sprawdzić kod wyjścia niż parsować dane wyjściowe.
Dale Forester
git status --porcelainjest twoim przyjacielem, jeśli chcesz przeanalizować dane wyjściowe według skryptu, spójrz na połączony dokument, który pokazuje kilka innych przydatnych opcji
stefanB
Cześć, nie działa z bardzo starą git status --porcelain error: unknown option wersją Git: porcelana w wersji 1.6.0 :-)
Laryx Decidua
@ user465139 jest poprawny ... potrzebujesz git 1.7.0 lub nowszej (opcja porcelany nie była dodawana do tego czasu).
mason81
13

Spróbuj uruchomić git statusplik. Wypisuje błąd, jeśli nie jest śledzony przez git

PS$> git status foo.txt
error: pathspec 'foo.txt' did not match any file(s) known to git.
JaredPar
źródło
Łał. Musiałem uruchomić go w katalogu i działało to tak, jakby sprawdzało całe repozytorium. Dzięki.
Dale Forester
4
Właściwie, jeśli uruchomię git status trackedfile, dostaję kod wyjścia 1 (oczekiwany jest 0 użyteczny), ale nie daje mi „błędu:” w danych wyjściowych. Wolę parsować kod wyjścia niż ciąg znaków.
Dale Forester
43
Uważam, że nie pojawia się błąd, jeśli uruchomię status git na pliku, który istnieje w mojej kopii roboczej git, ale który jest wykluczony przez .gitignore. (To znaczy, że ta odpowiedź nie zadziała.)
JellicleCat
Należy pamiętać, że nie działa dobrze, jeśli plik znajduje się na liście ignorowanych, tj. W pliku.gitignore
Robin Hsu
8
To nie działa. Zawsze drukuje to samo, nawet jeśli plik nie istnieje. $ git status notthere:On branch master nothing to commit, working directory clean
Chloe,
6

Nie znam żadnego polecenia git, które daje „zły” kod wyjścia, ale wydaje się, że łatwym sposobem byłoby użycie polecenia git, które nie daje danych wyjściowych dla pliku, który nie jest śledzony, takiego jak git-log lub git-ls-files. W ten sposób nie musisz tak naprawdę analizować, możesz uruchomić go za pomocą innego prostego narzędzia, takiego jak grep, aby sprawdzić, czy jest jakieś wyjście.

Na przykład,

git-ls-files plik_testowy.c | grep

wyjdzie z kodem zerowym, jeśli plik jest śledzony, ale kodem wyjścia, jeśli plik nie jest śledzony.

Jay Walker
źródło
3

Proponuję niestandardowy alias dla ciebie .gitconfig.

Musisz zrobić:

1) Za pomocą polecenia git:

git config --global alias.check-file <command>

2) Edycja ~/.gitconfigi dodanie tego wiersza w sekcji aliasów:

[alias]
    check-file = "!f() { if [ $# -eq 0 ]; then echo 'Filename missing!'; else tracked=$(git ls-files ${1}); if [[ -z ${tracked} ]]; then echo 'File not tracked'; else echo 'File tracked'; fi; fi;  };  f"

Po uruchomieniu polecenia (1) lub zapisanego pliku (2) w obszarze roboczym możesz go przetestować:

$ git check-file
$ Filename missing 

$ git check-file README.md
$ File tracked 

$ git check-file foo
$ File not tracked
Luca Davanzo
źródło
2

użycie git logda informacje o tym. Jeśli plik jest śledzony w git, polecenie wyświetla niektóre wyniki (dzienniki). W przeciwnym razie jest pusty.

Na przykład jeśli plik jest śledzony przez git,

root@user-ubuntu:~/project-repo-directory# git log src/../somefile.js
commit ad9180b772d5c64dcd79a6cbb9487bd2ef08cbfc
Author: User <[email protected]>
Date:   Mon Feb 20 07:45:04 2017 -0600

    fix eslint indentation errors
....
....

Jeśli plik nie jest śledzony,

root@user-ubuntu:~/project-repo-directory# git log src/../somefile.js
root@user-ubuntu:~/project-repo-directory#
SuperNova
źródło
1

Tylko moje dwa centy:

git ls-files | grep -x relative/path

gdzie relative/pathmożna to łatwo ustalić, naciskając tabw powłoce autouzupełniania. Dodaj dodatkowy, | wc -l aby uzyskać wynik 1 lub 0.

andreee
źródło
W zależności od ścieżki (np. Jeśli zawiera kropkę), należy dodać grepopcję --fixed-strings.
EndlosSchleife