Kluczem do niezawodnego „skryptowania” Gita jest użycie poleceń „hydraulicznych”.
Deweloperzy zwracają uwagę podczas zmiany poleceń hydraulicznych, aby upewnić się, że zapewniają bardzo stabilne interfejsy (tj. Dana kombinacja stanu repozytorium, standardowego wejścia, opcji wiersza poleceń, argumentów itp. Spowoduje wygenerowanie tego samego wyniku we wszystkich wersjach Gita, w których polecenie / opcja istnieje). Nowe warianty danych wyjściowych w komendach hydraulicznych można wprowadzić za pomocą nowych opcji, ale to nie może wprowadzić żadnych problemów dla programów, które zostały już napisane w stosunku do starszych wersji (nie korzystałyby z nowych opcji, ponieważ nie istniały (a przynajmniej były nieużywane) w momencie pisania skryptu).
Niestety „codzienne” polecenia Git to polecenia „porcelanowe”, więc większość użytkowników Gita może nie być zaznajomiona z poleceniami hydraulicznymi. Rozróżnienie między porcelaną a poleceniem hydrauliki jest wykonane na głównej stronie man git (patrz podrozdziały zatytułowane Polecenia wysokiego poziomu (porcelana) i Polecenia niskiego poziomu (hydraulika) .
Aby dowiedzieć się o niezatwierdzonych zmianach, prawdopodobnie będziesz potrzebować git diff-index
(porównaj indeks (i być może śledzone fragmenty działającego drzewa) z jakimś innym drzewiastym (np. HEAD
)), Może git diff-files
(porównaj działające drzewo z indeksem) i ewentualnie git ls-files
(wylistuj pliki; np. Lista nieśledzona , nieignorowane pliki).
(Zauważ, że w poniższych poleceniach HEAD --
użyto zamiast, HEAD
ponieważ w przeciwnym razie polecenie nie powiedzie się, jeśli istnieje plik o nazwie HEAD
.)
Aby sprawdzić, czy repozytorium wprowadziło zmiany (jeszcze nie zatwierdzone):
git diff-index --quiet --cached HEAD --
- Jeśli wyjdzie z,
0
wtedy nie będzie żadnych różnic ( 1
oznacza, że były różnice).
Aby sprawdzić, czy działające drzewo ma zmiany, które można wprowadzić:
git diff-files --quiet
- Kod wyjścia jest taki sam jak dla
git diff-index
( 0
== brak różnic; 1
== różnice).
Aby sprawdzić, czy kombinacja indeksu i plików śledzonych w drzewie roboczym ma zmiany w odniesieniu do HEAD
:
git diff-index --quiet HEAD --
- To jest jak połączenie dwóch poprzednich. Jedną z głównych różnic jest to, że nadal będzie zgłaszać „brak różnic”, jeśli masz zmianę etapową, którą „cofnąłeś” w działającym drzewie (wróciłeś do zawartości, która jest w nim
HEAD
). W tej samej sytuacji oba oddzielne polecenia zwracałyby raporty „obecnych różnic”.
Wspomniałeś także o nieśledzonych plikach. Możesz oznaczać „nieśledzony i niezauważony” lub zwykły „nieśledzony” (w tym pliki ignorowane). Tak czy inaczej, git ls-files
narzędzie do pracy:
W przypadku „nieśledzonego” (obejmie pliki ignorowane, jeśli są obecne):
git ls-files --others
W przypadku „nieśledzonych i niezauważonych”:
git ls-files --exclude-standard --others
Moją pierwszą myślą jest sprawdzenie, czy te komendy mają dane wyjściowe:
test -z "$(git ls-files --others)"
- Jeśli zakończy działanie, oznacza
0
to, że nie ma żadnych nieśledzonych plików. Jeśli zakończy działanie, oznacza 1
to, że pliki nie są śledzone.
Istnieje niewielka szansa, że przełoży się to na nieprawidłowe wyjścia z git ls-files
raportów na „brak nieśledzonych plików” (oba powodują niezerowe wyjścia z powyższego polecenia). Trochę bardziej niezawodna wersja może wyglądać następująco:
u="$(git ls-files --others)" && test -z "$u"
- Pomysł jest taki sam jak w poprzednim poleceniu, ale umożliwia
git ls-files
rozprzestrzenianie się nieoczekiwanych błędów . W takim przypadku niezerowe wyjście może oznaczać „istnieją nieśledzone pliki” lub może oznaczać błąd. Jeśli zamiast tego chcesz, aby wyniki „błąd” były połączone z wynikiem „brak nieśledzonych plików”, użyj test -n "$u"
(gdzie wyjście z 0
oznacza „niektóre nieśledzone pliki”, a niezerowe oznacza błąd lub „brak nieśledzonych plików”).
Innym pomysłem jest użycie --error-unmatch
niezerowego wyjścia, gdy nie ma nieśledzonych plików. Wiąże się to również z ryzykiem, że „brak nieśledzonych plików” (wyjście 1
) z „wystąpił błąd” (wyjście niezerowe, ale prawdopodobnie 128
). Ale sprawdzanie 0
vs 1
vs niezerowych kodów wyjścia jest chyba dość wytrzymała:
git ls-files --others --error-unmatch . >/dev/null 2>&1; ec=$?
if test "$ec" = 0; then
echo some untracked files
elif test "$ec" = 1; then
echo no untracked files
else
echo error from ls-files
fi
Każdy z powyższych git ls-files
przykładów może wziąć, --exclude-standard
jeśli chcesz wziąć pod uwagę tylko nieśledzone i niezauważone pliki.