Chciałbym tylko zwrócić uwagę na inne możliwe podejście - i to za pomocą git
git-notes (1) , istniejącego od wersji 1.6.6 ( Note to Self - Git ) (używam git
wersji 1.7.9.5).
Zasadniczo git svn
klonowałem repozytorium SVN z historią liniową (bez standardowego układu, bez rozgałęzień, bez tagów) i chciałem porównać numery wersji w sklonowanym git
repozytorium. Ten klon git nie ma domyślnie tagów, więc nie mogę go użyć git describe
. Strategia tutaj prawdopodobnie działałaby tylko dla historii liniowej - nie jestem pewien, jak to się skończy z fuzjami itp .; ale oto podstawowa strategia:
- Zapytaj
git rev-list
o listę wszystkich historii zatwierdzeń
- Ponieważ
rev-list
domyślnie jest w „odwrotnym porządku chronologicznym”, użyjemy jego --reverse
przełącznika, aby uzyskać listę zatwierdzeń posortowanych według najstarszych
- Użyj
bash
powłoki do
- zwiększyć zmienną licznika przy każdym zatwierdzeniu jako licznik zmian,
- wygeneruj i dodaj „tymczasową” notatkę git dla każdego zatwierdzenia
- Następnie przejrzyj dziennik za pomocą
git log
przy pomocy --notes
, co spowoduje również zrzucenie notatki zatwierdzenia, która w tym przypadku byłaby „numerem wersji”
- Po zakończeniu usuń tymczasowe notatki ( NB: Nie jestem pewien, czy te notatki są
git status
zatwierdzone, czy nie; tak naprawdę nie pojawiają się )
Po pierwsze, zwróćmy uwagę, że git
ma domyślną lokalizację notatek - ale możesz także określić ref
(erence) dla notatek - która zapisałaby je w innym katalogu .git
; na przykład, gdy jesteś w git
folderze repo, możesz zadzwonić, git notes get-ref
aby zobaczyć, jaki to będzie katalog:
$ git notes get-ref
refs/notes/commits
$ git notes --ref=whatever get-ref
refs/notes/whatever
Należy zauważyć, że jeśli używasz notes add
znaku a --ref
, musisz także użyć tego odwołania ponownie - w przeciwnym razie mogą pojawić się błędy typu „ Nie znaleziono notatki dla obiektu XXX ... ”.
W tym przykładzie zdecydowałem się nazwać ref
notatkę „linrev” (dla wersji liniowej) - oznacza to również, że jest mało prawdopodobne, że procedura będzie kolidować z już istniejącymi nutami. Używam również --git-dir
przełącznika, ponieważ będąc git
nowicjuszem miałem problemy z jego zrozumieniem - dlatego chciałbym „zapamiętać na później” :)
; i używam również --no-pager
do tłumienia pojawiania się less
podczas używania git log
.
Zakładając, że jesteś w katalogu z podfolderem, myrepo_git
który jest git
repozytorium; można zrobić:
### check for already existing notes:
$ git --git-dir=./myrepo_git/.git notes show
# error: No note found for object 04051f98ece25cff67e62d13c548dacbee6c1e33.
$ git --git-dir=./myrepo_git/.git notes --ref=linrev show
# error: No note found for object 04051f98ece25cff67e62d13c548dacbee6c1e33.
### iterate through rev-list three, oldest first,
### create a cmdline adding a revision count as note to each revision
$ ix=0; for ih in $(git --git-dir=./myrepo_git/.git rev-list --reverse HEAD); do \
TCMD="git --git-dir=./myrepo_git/.git notes --ref linrev"; \
TCMD="$TCMD add $ih -m \"(r$((++ix)))\""; \
echo "$TCMD"; \
eval "$TCMD"; \
done
# git --git-dir=./myrepo_git/.git notes --ref linrev add 6886bbb7be18e63fc4be68ba41917b48f02e09d7 -m "(r1)"
# git --git-dir=./myrepo_git/.git notes --ref linrev add f34910dbeeee33a40806d29dd956062d6ab3ad97 -m "(r2)"
# ...
# git --git-dir=./myrepo_git/.git notes --ref linrev add 04051f98ece25cff67e62d13c548dacbee6c1e33 -m "(r15)"
### check status - adding notes seem to not affect it:
$ cd myrepo_git/
$ git status
# # On branch master
# nothing to commit (working directory clean)
$ cd ../
### check notes again:
$ git --git-dir=./myrepo_git/.git notes show
# error: No note found for object 04051f98ece25cff67e62d13c548dacbee6c1e33.
$ git --git-dir=./myrepo_git/.git notes --ref=linrev show
# (r15)
### note is saved - now let's issue a `git log` command, using a format string and notes:
$ git --git-dir=./myrepo_git/.git --no-pager log --notes=linrev --format=format:"%h: %an: %ad: >>%s<< %N" HEAD
# 04051f9: _user_: Sun Apr 21 18:29:02 2013 +0000: >>test message 15 << (r15)
# 77f3902: _user_: Sun Apr 21 18:29:00 2013 +0000: >>test message 14<< (r14)
# ...
# 6886bbb: _user_: Sun Apr 21 17:11:52 2013 +0000: >>initial test message 1<< (r1)
### test git log with range:
$ git --git-dir=./myrepo_git/.git --no-pager log --notes=linrev --format=format:"%h: %an: %ad: >>%s<< %N" HEAD^..HEAD
# 04051f9: _user_: Sun Apr 21 18:29:02 2013 +0000: >>test message 15 << (r15)
### erase notes - again must iterate through rev-list
$ ix=0; for ih in $(git --git-dir=./myrepo_git/.git rev-list --reverse HEAD); do \
TCMD="git --git-dir=./myrepo_git/.git notes --ref linrev"; \
TCMD="$TCMD remove $ih"; \
echo "$TCMD"; \
eval "$TCMD"; \
done
# git --git-dir=./myrepo_git/.git notes --ref linrev remove 6886bbb7be18e63fc4be68ba41917b48f02e09d7
# Removing note for object 6886bbb7be18e63fc4be68ba41917b48f02e09d7
# git --git-dir=./myrepo_git/.git notes --ref linrev remove f34910dbeeee33a40806d29dd956062d6ab3ad97
# Removing note for object f34910dbeeee33a40806d29dd956062d6ab3ad97
# ...
# git --git-dir=./myrepo_git/.git notes --ref linrev remove 04051f98ece25cff67e62d13c548dacbee6c1e33
# Removing note for object 04051f98ece25cff67e62d13c548dacbee6c1e33
### check notes again:
$ git --git-dir=./myrepo_git/.git notes show
# error: No note found for object 04051f98ece25cff67e62d13c548dacbee6c1e33.
$ git --git-dir=./myrepo_git/.git notes --ref=linrev show
# error: No note found for object 04051f98ece25cff67e62d13c548dacbee6c1e33.
Tak więc, przynajmniej w moim konkretnym przypadku w pełni liniowej historii bez rozgałęzień, numery wersji wydają się pasować do tego podejścia - i dodatkowo wydaje się, że to podejście pozwoli na użycie git log
z zakresami wersji, przy jednoczesnym uzyskaniu odpowiednich numerów wersji - YMMV jednak w innym kontekście ...
Mam nadzieję, że to komuś pomoże,
zdrowie!
EDYCJA: Ok, tutaj jest trochę łatwiej, z git
aliasami dla powyższych pętli, nazwanymi setlinrev
i unsetlinrev
; znajdując się w folderze repozytorium git, wykonaj następujące czynności ( zwróć uwagę na paskudną bash
ucieczkę, zobacz także # 16136745 - Dodaj alias Git zawierający średnik ):
cat >> .git/config <<"EOF"
[alias]
setlinrev = "!bash -c 'ix=0; for ih in $(git rev-list --reverse HEAD); do \n\
TCMD=\"git notes --ref linrev\"; \n\
TCMD=\"$TCMD add $ih -m \\\"(r\\$((++ix)))\\\"\"; \n\
#echo \"$TCMD\"; \n\
eval \"$TCMD\"; \n\
done; \n\
echo \"Linear revision notes are set.\" '"
unsetlinrev = "!bash -c 'ix=0; for ih in $(git rev-list --reverse HEAD); do \n\
TCMD=\"git notes --ref linrev\"; \n\
TCMD=\"$TCMD remove $ih\"; \n\
#echo \"$TCMD\"; \n\
eval \"$TCMD 2>/dev/null\"; \n\
done; \n\
echo \"Linear revision notes are unset.\" '"
EOF
... więc możesz po prostu wywołać git setlinrev
przed próbą wykonania dziennika zawierającego liniowe notatki z rewizji; i git unsetlinrev
aby usunąć te notatki, gdy skończysz; przykład z katalogu git repo:
$ git log --notes=linrev --format=format:"%h: %an: %ad: >>%s<< %N" HEAD^..HEAD
04051f9: _user_: Sun Apr 21 18:29:02 2013 +0000: >>test message 15 <<
$ git setlinrev
Linear revision notes are set.
$ git log --notes=linrev --format=format:"%h: %an: %ad: >>%s<< %N" HEAD^..HEAD
04051f9: _user_: Sun Apr 21 18:29:02 2013 +0000: >>test message 15 << (r15)
$ git unsetlinrev
Linear revision notes are unset.
$ git log --notes=linrev --format=format:"%h: %an: %ad: >>%s<< %N" HEAD^..HEAD
04051f9: _user_: Sun Apr 21 18:29:02 2013 +0000: >>test message 15 <<
Czas potrzebny powłoce na uzupełnienie tych aliasów będzie zależał od wielkości historii repozytorium.