Zignoruj ​​nowe zatwierdzenia dla modułu podrzędnego git

83

tło

Korzystanie z Git 1.8.1.1 w systemie Linux. Repozytorium wygląda następująco:

master
  book

Podmoduł został utworzony w następujący sposób:

$ cd /path/to/master
$ git submodule add https://[email protected]/user/repo.git book

bookModułem jest czysty:

$ cd /path/to/master/book/
$ git status
# On branch master
nothing to commit, working directory clean

Problem

Z drugiej strony wzorzec pokazuje, że dla podmodułu książki istnieją „nowe zatwierdzenia”:

$ cd /path/to/master/
$ git status
# On branch master
# Changes not staged for commit:
#   (use "git add <file>..." to update what will be committed)
#   (use "git checkout -- <file>..." to discard changes in working directory)
#
#       modified:   book (new commits)
#
no changes added to commit (use "git add" and/or "git commit -a")

Git powinien całkowicie zignorować katalog podmodułów, aby master również był czysty:

$ cd /path/to/master/
$ git status
# On branch master
nothing to commit, working directory clean

Nieudana próba nr 1 - zabrudzona

Wewnątrz pliku master/.gitmodulesjest następująca, zgodnie z tą odpowiedzią :

[submodule "book"]
        path = book
        url = https://[email protected]/user/repo.git
        ignore = dirty

Nieudana próba nr 2 - nieśledzony

Zmieniono master/.gitmodulesna następujące, zgodnie z tą odpowiedzią :

[submodule "book"]
        path = book
        url = https://[email protected]/user/repo.git
        ignore = untracked

Nieudana próba nr 3 - showUntrackedFiles

Zredagowano master/.git/confignastępujące, zgodnie z tą odpowiedzią :

[status]
   showUntrackedFiles = no

Nieudana próba nr 4 - zignoruj

Dodano katalog książek do głównego pliku ignorowania:

$ cd /path/to/master/
$ echo book > .gitignore

Nieudana próba nr 5 - klon

Dodano katalog książek do wzorca w następujący sposób:

$ cd /path/to/master/
$ rm -rf book
$ git clone https://[email protected]/user/repo.git book

Pytanie

W jaki sposób bookmoduł podrzędny może znajdować się we własnym katalogu masterrepozytorium w repozytorium, a git może zignorować bookmoduł podrzędny? Oznacza to, że nie powinny być wyświetlane następujące informacje:

#
#       modified:   book (new commits)
#

Jak pominąć ten komunikat podczas wykonywania git statusw repozytorium głównym?

Artykuł o pułapkach podmodułu git sugeruje, że jest to niewłaściwe użycie modułu podrzędnego?

Dave Jarvis
źródło
3
Zwykle używasz modułów podrzędnych, jeśli chcesz połączyć repozytorium z określoną wersją innego repozytorium i śledzić to. Ale to nie wydaje się być tym, czego chcesz. Chcesz po prostu użyć repozytorium w innym, bez śledzenia go. Nie dodawaj go wtedy jako modułu podrzędnego.
Felix Kling
@FelixKling, jeśli dodasz takie repozytoria w ten sposób i wypchniesz je do GitHub, czy utworzy on tylko link do niego bez kopiowania zawartości tych folderów?
Roman Bekkiev
@Roland: Podmoduły to tylko pliki z odniesieniem do wersji innego repozytorium. Po zainicjowaniu w lokalnej kopii repozytorium są zastępowane rzeczywistą zawartością repozytorium.
Felix Kling
2
Myślę, że szukasz „ignore = all”
greuze
1
Z Git 2.13 (Q2 2017) będziesz mógł rozważyć git config submodule.<name>.active false. Zobacz moją odpowiedź poniżej
VonC

Odpowiedzi:

60

Aby dołączyć inne repozytorium, które nie musi być śledzone w swoim super-repozytorium, spróbuj tego:

$ cd /path/to/master/
$ rm -rf book
$ git clone https://[email protected]/user/repo.git book
$ git add book
$ echo "book" >> .gitignore

Następnie zatwierdź.

Jak stwierdzono w artykule o pułapkach powiązanych modułów git podrzędnych :

... jedynym powiązaniem między rodzicem a modułem podrzędnym jest [ta] zarejestrowana wartość wyewidencjonowanego SHA podmodułu, która jest przechowywana w zatwierdzeniach elementu nadrzędnego.

Oznacza to, że podmoduł nie jest zapisywany przez swoją wyewidencjonowaną gałąź lub tag, ale zawsze przez określone zatwierdzenie; to zatwierdzenie (SHA) jest zapisywane w super-repozytorium (tym zawierającym podmoduł) jak zwykły plik tekstowy (jest oczywiście oznaczony jako odniesienie).

Kiedy wyewidencjonujesz inne zatwierdzenie w module podrzędnym lub dokonasz w nim nowego zatwierdzenia, super-repozytorium zobaczy, że jego wyewidencjonowany SHA uległ zmianie. Wtedy otrzymujesz modified (new commits)linię od git status.

Aby to wyeliminować, możesz:

  • git submodule update, co spowoduje zresetowanie modułu podrzędnego do zatwierdzenia aktualnie zapisanego w super-repozytorium (szczegóły patrz strona git submodulepodręcznika ; lub
  • git add book && git commit aby zapisać nowy SHA w super-repozytorium.

Jak wspomniano w komentarzach, rozważ porzucenie modułu bookpodrzędnego: sklonuj go w super-repozytorium, jeśli śledzenie jego stanu jako część super-repozytorium nie jest konieczne.

Nevik Rehnel
źródło
3
Wow, teraz rozumiem, dlaczego supermoduł musi znać wersję submodułu. Oczywiście ma to sens git add book && git commit. Nie zdawałem sobie sprawy, że git może faktycznie zapewnić synchronizację dwóch repozytoriów.
Sergey Orshanskiy
103

Po prostu biegnij:

$ git submodule update

Spowoduje to przywrócenie modułu podrzędnego do starego zatwierdzenia (określonego w repozytorium nadrzędnego) bez aktualizowania repozytorium nadrzędnego o najnowszą wersję modułu podrzędnego.

Shiv Kumar
źródło
6
Nie, nie jest, to nie zmieni statusu.
Ed Bishop
Dlaczego dokładnie OP chciałby nie mieć najnowszy z bookrepozytorium? Nie sądzę, aby twoja odpowiedź miała sens w tym kontekście.
Alexis Wilke
@AlexisWilke i jeśli interfejs książki zmieni się dramatycznie i OP nie będzie miał czasu na dokonywanie zmian w głównym repozytorium?
Logman
To jest odpowiedź, której szukałem!
LLSv2.0
21

Istnieją dwa rodzaje powiadomień o zmianach, które można ukryć (od git 1.7.2).

Pierwsza to nieśledzona zawartość, która ma miejsce, gdy wprowadzasz zmiany w module podrzędnym, ale jeszcze ich nie zatwierdziłeś. Repozytorium nadrzędne to zauważa, a status git zgłasza to odpowiednio:

modified: book (untracked content)

Możesz je stłumić za pomocą:

[submodule "book"]
    path = modules/media
    url = https://[email protected]/user/repo.git
    ignore = dirty

Jednak po zatwierdzeniu tych zmian repozytorium nadrzędne ponownie zwróci uwagę i odpowiednio je zgłosi:

modified:   book (new commits)

Jeśli chcesz je również ukryć, musisz zignorować wszystkie zmiany

[submodule "book"]
    path = book
    url = https://[email protected]/user/repo.git
    ignore = all
Greuze
źródło
Wyobraź sobie, że dodałem ignore = allopcję do wszystkich modułów podrzędnych. Ostatecznie niektóre moduły mają nowe zatwierdzenia, które zostały wypchnięte. Jeśli ktoś następnie sklonuje super-repozytorium, czy będzie on w starym stanie podmodułów, czy też pobierze najnowsze?
FelikZ
Za pomocą polecenia git clone --recursive git@...uzyskasz stary stan podmodułów. Aby je zaktualizować, będziesz potrzebować czegoś takiego jak git submodule foreach "git pull"po sklonowaniu
greuze
1
Niestety ignore = allopcja nie ignoruje nowych zatwierdzeń podmodułu. Używam git w wersji 1.7.1. Każdy pomysł?
Romulus
10

Git 2.13 (drugi kwartał 2017 r.) Doda kolejny sposób na włączenie modułu podrzędnego, który nie musi być śledzony przez repozytorium nadrzędne.

W przypadku PO:

git config submodule.<name>.active false

Zobacz zatwierdzenie 1b614c0 , zatwierdzenie 1f8d711 , zatwierdzenie bb62e0a , zatwierdzenie 3e7eaed , zatwierdzenie a086f92 (17 marca 2017 r.) I zatwierdzenie ee92ab9 , zatwierdzenie 25b31f1 , zatwierdzenie e7849a9 , zatwierdzenie 6dc9f01 , zatwierdzenie 5c2bd8b (16 marca 2017 r.) Autorstwa Brandona ( mbrandonw) .
(Scalone przez Junio ​​C Hamano - gitster- w zatwierdzeniu a93dcb0 , 30 marca 2017 r.)

submodule: oddziel adres URL i zainteresowanie podmodułem

Obecnie submodule.<name>.urlopcja config służy do określenia, czy dany podmoduł jest interesujący dla użytkownika. W rezultacie staje się to kłopotliwe w świecie, w którym chcemy mieć różne podmoduły sprawdzane w różnych drzewach roboczych lub bardziej uogólniony mechanizm wyboru, które podmoduły są interesujące.

W przyszłości z obsługą podmodułów w obszarze roboczym będzie wiele drzew roboczych, z których każde może wymagać sprawdzenia tylko podzbioru modułów podrzędnych.
Adres URL (gdzie można uzyskać repozytorium podmodułów) nie powinien różnić się między różnymi drzewami roboczymi.

Dla użytkowników może być również wygodne łatwiejsze określenie grup podmodułów, którymi są zainteresowani, zamiast uruchamiania " git submodule init <path>" każdego podmodułu, który chcą sprawdzić w swoim drzewie roboczym.

W tym celu wprowadzono dwie opcje konfiguracyjne submodule.activei submodule.<name>.active.

  • submodule.activeConfig posiada pathspec która określa Submoduły powinny istnieć w drzewie roboczym.
    • submodule.<name>.activeConfig jest logiczna flag służy do wskazania, czy ten konkretny modułem powinna istnieć w drzewie roboczego.

Należy zauważyć, że submodule.activedziała inaczej niż pozostałe opcje konfiguracyjne, ponieważ pobiera specyfikację ścieżki.
Pozwala to użytkownikom na przyjęcie co najmniej dwóch nowych przepływów pracy:

  1. Podmoduły mogą być zgrupowane z głównym katalogiem, tak że ścieżka np. „ lib/” Obejmowałaby wszystkie moduły biblioteczne, aby umożliwić tym, którzy są zainteresowani modułami bibliotecznymi, ustawienie " submodule.active = lib/" tylko raz, aby powiedzieć, że wszystkie moduły w ' lib/' są ciekawy.
  2. Po wynalezieniu funkcji pathspec-attribute, użytkownicy mogą oznaczać podmoduły atrybutami, aby je pogrupować, tak aby szeroka ścieżka z wymaganiami atrybutów, np. „ :(attr:lib)”, Mogła być użyta do stwierdzenia, że ​​dowolne i wszystkie moduły z libatrybutem „ ” są interesujące.
    Ponieważ .gitattributesplik, podobnie jak .gitmodulesplik, jest śledzony przez superprojekt, kiedy podmoduł porusza się w drzewie superprojektu, projekt może dostosować ścieżkę do atrybutu .gitattributes, tak samo jak może dostosować ścieżkę, w której znajduje się podmoduł .gitmodules.
VonC
źródło
Jak dokładnie znaleźć <name>podmoduł w istniejącym projekcie?
ideasman42
@ ideasman42 Czytanie konfiguracji w .gitmodules powinno pomóc: stackoverflow.com/a/12641787/6309
VonC
Ach, to tylko wartość z .git/config->[submodule "<name>"]
ideasman42
1
Nie działa dla mnie. Oto co robię: 1) git clone with --recursive; 2) ustaw jako odpowiedź git config; 3) do git checkout, git pull to checkout ostatniego podmodułu; Nadal otrzymujesz „(nowe zatwierdzenia)”.
Wu Baiquan
2
@VonC Przed wysłaniem wiadomości do Ciebie wypróbowałem oba (z istniejącym repozytorium, a także z nowym zainicjowanym repozytorium), w obu przypadkach nie zadziałało.
Jeżozwierz
3

Odpowiedź Nevika Rehnela jest z pewnością poprawna, jeśli chodzi o to, o co pytasz: nie chciałem mieć modułu podrzędnego , jak do cholery mam wyjść z tej sytuacji ?! .

Tylko, jeśli twój masterprojekt wymaga modułu bookpodrzędnego, dobrym gestem jest zachowanie go jako takiego, ponieważ w ten sposób inni użytkownicy, którzy sprawdzają twój projekt, mogą wtedy cieszyć się brakiem specjalnego gitpolecenia do uruchomienia (cóż ... jest kilka specjalnych poleceń do użycia podmoduły, ale ogólnie rzecz biorąc, zarządzanie nimi jest prostsze).

W twoim przypadku dokonujesz zmian w bookrepozytorium iw pewnym momencie zatwierdzasz te zmiany. Oznacza to, że masz nowe zatwierdzenia w tym module podrzędnym, które mają nową referencję SHA1.

To, co musisz zrobić w katalogu głównym, to zatwierdzić te zmiany w repozytorium głównym.

cd /path/to/master
git commit . -m "Update 'book' in master"

Spowoduje to zaktualizowanie odniesienia SHA1 w master do najnowszej wersji dostępnej w bookrepozytorium. W rezultacie to zatwierdzenie pozwala innym na pobranie wszystkich master& bookrepozytoriów na końcówce.

W efekcie otrzymujesz jeszcze jedno zatwierdzenie za każdym razem, gdy wprowadzisz zmiany w module podrzędnym. Jest to półprzezroczyste, jeśli wprowadzisz również zmiany w niektórych plikach w masterrepozytorium, ponieważ zatwierdzisz oba w tym samym czasie.

Alexis Wilke
źródło
-5

Biegać

git submodule update 

na poziomie głównym.

think2010
źródło
Tylko dla każdego, kto się zastanawia. W moim przypadku (i OP?) To nie zmienia tego git status, co mówi. Nadal uważa, że ​​zaszły zmiany.
skwaryzm
Maxim