Wprowadziłem kilka zmian w mojej gałęzi master i chcę wprowadzić je wcześniej. kiedy wybieram następujące zatwierdzenia, utknąłem na fd9f578, gdzie git mówi:
$ git cherry-pick fd9f578
fatal: Commit fd9f57850f6b94b7906e5bbe51a0d75bf638c74d is a merge but no -m option was given.
Co git próbuje mi powiedzieć i czy wybranie właściwego rozwiązania jest tutaj przydatne? Gałąź główna zawiera zmiany w plikach, które zostały zmodyfikowane w gałęzi upstream, więc jestem pewien, że wystąpią pewne konflikty scalania, ale nie są one takie złe, aby je wyjaśnić. Wiem, które zmiany są potrzebne gdzie.
To są zobowiązania, które chcę wprowadzić na początku.
e7d4cff added some comments...
23e6d2a moved static strings...
44cc65a incorporated test ...
40b83d5 whoops delete whitspace...
24f8a50 implemented global.c...
43651c3 cleaned up ...
068b2fe cleaned up version.c ...
fd9f578 Merge branch 'master' of ssh://extgit/git/sessions_common
4172caa cleaned up comments in sessions.c ...
źródło
git rebase
- to jak scalenie, ale zamiast zintegrować dwie gałęzie, przeszczepia jedną, aby usiąść na drugiej.git show
i tym podobne).git reset --hard HEAD@{1}
aby odzyskać swoje brakujące zatwierdzenie.git reset
nie ogranicza się do cofania się w historii.git checkout -b mybranch HEAD@{1}
też by działał.git merge
może mieć niezamierzone konsekwencje. To polecenie doda wszystkie inne (starsze) zatwierdzenia, które istnieją w gałęzi nadrzędnej. Zwykle ludzie wybierają wiśniowe wybieranie, ponieważ nie chcą innych zobowiązań. Upewnij się, że dokładnie sprawdzasz, czy wprowadzasz tylko te zmiany, które chcesz!-m
oznacza numer rodzica.Z git doc:
Na przykład, jeśli twoje drzewo zatwierdzeń jest jak poniżej:
następnie
git cherry-pick E
będzie produkować kwestię Ci zmierzyć.git cherry-pick E -m 1
oznacza używanieD-E
, podczas gdygit cherry-pick E -m 2
oznacza używanieB-C-E
.źródło
@ Odpowiedź Borealid jest poprawna, ale załóżmy, że nie zależy ci na zachowaniu dokładnej historii scalania gałęzi i po prostu chcesz wybrać jej zlinearyzowaną wersję. Oto prosty i bezpieczny sposób, aby to zrobić:
Stan początkowy: jesteś na gałęzi
X
i chcesz wybijać zatwierdzeniaY..Z
.git checkout -b tempZ Z
git rebase Y
git checkout -b newX X
git cherry-pick Y..tempZ
git branch -D tempZ
To polega na stworzeniu gałęzi
tempZ
opartej naZ
, ale z historią odY
zlinearyzowania, a następnie wybranie go na kopięX
tzwnewX
. (Bezpieczniej jest to zrobić w nowej gałęzi, niż mutowaćX
.) Oczywiście w kroku 4 mogą wystąpić konflikty, które będziesz musiał rozwiązać w zwykły sposób (cherry-pick
działa bardzo podobnierebase
pod tym względem). Na koniec usuwatempZ
gałąź tymczasową .Jeśli krok 2 wyświetla komunikat „Aktualna gałąź temp. Z jest aktualna”, to
Y..Z
jest już liniowy, więc po prostu zignoruj ten komunikat i przejdź do kroku 3.Następnie sprawdź
newX
i sprawdź, czy zrobiłeś to, co chciałeś.(Uwaga: nie jest to to samo, co proste
git rebase X
na gałęziZ
, ponieważ nie zależy w żaden sposób od relacji międzyX
iY
; mogą występować między wspólnym przodkiem aY
tym, czego nie chciałeś).źródło
git rebase Y
mówiCurrent branch tempZ is up to date
Y..Z
było to już liniowe. Możesz więc zignorować tę wiadomość i przejść do kroków 3 i 4.Uproszczać. Cherry-pick the commits. Nie wybieraj scalania.
Oto przepis zaakceptowanej odpowiedzi, który idealnie wyjaśnia zalety / ryzyko możliwych podejść:
Próbujesz wybrać fd9f578, który był połączeniem dwojga rodziców.
Zamiast wybierania scalenia, najprostszą rzeczą jest wybranie zatwierdzenia (ów), które faktycznie chcesz z każdej gałęzi scalania.
Ponieważ już się połączyłeś, prawdopodobnie wszystkie pożądane zmiany znajdują się na liście. Wybierz je bezpośrednio i nie musisz zadzierać z zatwierdzaniem scalania.
wyjaśnienie
Sposób, w jaki działa cherry-pick, polega na pobraniu różnicy reprezentowanej przez zestaw zmian (różnica między drzewem roboczym w tym punkcie a drzewem roboczym jego rodzica) i zastosowaniu zestawu zmian do bieżącej gałęzi.
Jeśli zatwierdzenie ma dwóch lub więcej rodziców, jak ma to miejsce w przypadku scalania, zatwierdzenie to również reprezentuje dwa lub więcej różnic. Błąd występuje z powodu niepewności, w odniesieniu do której należy zastosować różnicę.
alternatywy
Jeśli zdecydujesz, że musisz dołączyć scalenie vs wybranie odpowiednich zatwierdzeń, masz dwie opcje:
(Bardziej skomplikowane i niejasne; również odrzuca historię) możesz wskazać, który rodzic powinien zastosować.
Skorzystaj z
-m
opcji, aby to zrobić. Na przykładgit cherry-pick -m 1 fd9f578
użyje pierwszego elementu nadrzędnego wymienionego w scaleniu jako podstawy.Weź również pod uwagę, że wybranie zatwierdzenia scalania powoduje zwinięcie wszystkich zmian dokonanych w obiekcie nadrzędnym, którego nie określiłeś
-m
w tym zatwierdzeniu . Tracicie całą ich historię i glom razem wszystkie ich różnice. Twoja decyzja.(Prostszy i bardziej znany; zachowuje historię), którego możesz użyć
git merge
zamiastgit cherry-pick
.git merge
, spróbuje zastosować wszystkie zatwierdzenia, które istnieją w łączonej gałęzi i wypisać je indywidualnie w dzienniku git.źródło
Uproszczenie metody @Daira Hopwood jest dobre do wybrania jednego zatwierdzenia. Nie potrzebujesz tymczasowych oddziałów.
W przypadku autora:
następnie wykonaj:
źródło