Kezdők útmutatója az interaktív újraszabályozáshoz
@StrideStride
Informatika és szolgáltatások
Az év elején csináltam először interaktív rebase-t és lenyűgözött, hogy mit lehet vele csinálni. Eleinte kicsit bonyolultnak is találtam. Remélhetőleg ez az útmutató segít eloszlatni némi bizonytalanságot körülötte.
Amellett, mivel ez olyan erős, és lényegében újraírhatod a történelmet, egy kis figyelmeztetés, mielőtt elkezdjük: Sokféle nézet létezik a Gitről és arról, hogy az újraalapozás jó ötlet-e vagy sem. Ez a bejegyzés nem fog belemerülni ezekbe a vitákba, és pusztán az interaktív rebasing használatának alapjait kívánja végigjárni.
TL;DR
- Az interaktív rebasing sokféleképpen használható a commitok módosítására, például szerkesztésre, törlésre és squashelésre.
- Hogy megmondja a Gitnek, hol kezdje az interaktív újraalapozást, használja a módosítandó commitot közvetlenül megelőző commit SHA-1-jét vagy indexét.
- Az interaktív újraalapozás során, amikor a Git szünetet tart a szerkesztésre megjelölt commitnál, a munkafolyamat nem különbözik a normál commit folyamatától – a fájlokat szakaszolja, majd commitolja. Az egyetlen különbség, hogy a
git commit
helyett agit commit --amend
parancsot használod. - Az interaktív újraszerkesztés új SHA-1-eket hoz létre, ezért a legjobb, ha az interaktív újraszerkesztést olyan commitoknál használod, amelyeket nem toltál el egy távoli ágba.
A probléma
Ebben a példában egy olyan helyzetet dolgozunk fel, amikor egy feature branchben dolgozunk, és van néhány commit, amit szeretnénk módosítani vagy törölni. Így néz ki a git naplónk:
A fenti git naplóból itt van a két commit, amit módosítani szeretnénk: 4a4d705
– Ebben a commitban véletlenül elkövettünk egy összeolvadási konfliktust6c01350
– Ebben a commitban eltávolítottuk az összeolvadási konfliktust
Azt szeretnénk tenni, hogy visszamegyünk az időben az 4a4d705
-be, eltávolítjuk az összeolvadási konfliktust a commitban, majd töröljük az 6c01350
-t, mivel az összeolvadási konfliktus megoldódott, és már nincs szükségünk erre a commitra. Ez két okból is javulást jelent majd a commit-előzményekben:
- Nem lesznek törött commitjaink (egyesítési konfliktusok)
- Kizárólag értelmes commitjaink lesznek, nem lesznek olyan commitjaink, amelyek kizárólag egy kihagyott egyesítési konfliktus javításához kapcsolódnak
A megoldás
Ez a helyzet jó jelölt az interaktív újraszerkesztésre. Scott Chacon a Pro Git című könyvében az interaktív újraszerkesztést a következőképpen írja le: “Néha a javított dolgot … nem lehet módosítani az általa javított nem egészen tökéletes commithoz, mert az a commit mélyen el van temetve egy patch-sorozatban. Pontosan erre való az interaktív rebase: használd a rengeteg , commitok átrendezésével és szerkesztésével, valamint több commit egybe gyömöszölésével.”
Milyen commitokat akarunk módosítani?
Az interaktív rebase elindításához meg kell mondanunk a Gitnek, hogy mely commitokat akarjuk módosítani. Ezt úgy tesszük meg, hogy hivatkozunk a legkorábbi commitot közvetlenül megelőző commitra, amelyet módosítani szeretnénk. Vagy egyszerűen fogalmazva, Scott Chacon szerint “az utolsó commitra hivatkozunk, amelyet úgy akarunk megtartani, ahogy van”.
Nézzük meg a példánkat, hogy jobban megértsük. Kétféleképpen hivatkozhatunk erre a commitra:
Az SHA-1 alapján – Az utolsó commit, amelyet úgy akarunk megtartani, ahogy van, SHA-1 értéke 528f82e
így ezt átadhatjuk az interaktív rebase parancsunknak.
By Index – Az utolsó commit, amit meg akarunk tartani as-is, index pozíciója 3 (a Git nulla alapú indexelést használ), így átadhatjuk a HEAD~3
-ot az interaktív rebase parancsunknak.
Megjegyzés – Ha csak néhány commit van, amire interaktív rebase-t akarsz csinálni, az index használata valószínűleg egyszerűbb a legtöbb ember számára. Ha azonban sok commitod van, az SHA-1 használata valószínűleg egyszerűbb, így nem kell végigszámolnod a git naplót.
Interaktív rebasing indítása
Példánk alapján vagy:
$ git rebase -i 528f82e
Or
$ git rebase -i HEAD~3
futtatjuk, ami megnyitja ezt az ablakot a Vimben:
Figyeljük meg, hogy a commitok a git loggal ellentétes sorrendben vannak. A git logban a legfrissebb commit van felül. Ebben a nézetben a legfrissebb commit alul van. Figyeld meg azt is, hogy az alábbi megjegyzések hasznos listát adnak az egyes commitokhoz használható érvényes parancsokról.
Ha nem ismered a Vim-et, csak kattints minden egyes szóra pick
, amit szerkeszteni szeretnél, majd nyomd meg a <i>
billentyűt (a beszúrási módhoz). Ha végzett a gépeléssel, nyomja meg a <esc>
billentyűt a beszúrási módból való kilépéshez.
Példánkban a módosítani kívánt commithoz a edit
parancsot, a törölni kívánt commithoz pedig a drop
parancsot módosítottuk. Ezután a :wq
parancsot futtatjuk a mentéshez és kilépünk a Vim ablakból.
A commit módosítása
A terminálban a következő üzenetet látjuk:
Ez érthető, hogy a 4a4d705
-nél megálltunk. Ez a legrégebbi commit abban a commit-sorozatban, amelyet módosítani szeretnénk. Ezzel a commit-tal kezdünk, és végigmegyünk az egyes commitokon a legutóbbiig.
Emlékeztetőül: 4a4d705
volt az a commit, amelyikben az egyesítési konfliktus volt, amit véletlenül lekötöttünk. Amikor megnyitjuk a szerkesztőnket, ott látjuk az egyesítési konfliktust:
Az egyesítési konfliktust tehát kijavítjuk a fájlban, de most mit tegyünk? Ha kétségeink vannak, git status
:
Cool! Ez valóban hasznos. Látjuk, hogy jelenleg a 4a4d705
-t szerkesztjük, és látjuk a következő két commitot, amelyekkel ez után a következő után kell cselekednünk.
Az üzenet többi része egy ismerős munkafolyamatot magyaráz el nekünk. A Git közli velünk, hogy ha módosítani akarjuk a git commit --amend
commitot, akkor futtassuk a git commit --amend
-et. Ez lényegében úgy fog működni, mint a tipikus git commit
, amit egy normál munkafolyamatban használunk. Ennek az üzenetnek az alján látjuk, hogy a fájlunk módosult, tükrözve a módosításokat, amelyeket az imént végeztünk az egyesítési konfliktus megszüntetése érdekében. Át kell rendeznünk a fájlt, mielőtt commitolnánk. Ez nem különbözik a normál munkafolyamatoktól.
Mindössze annyit kell tennünk, hogy git add tempChanger.js
a szerkesztett fájlt színpadra állítjuk, majd git commit --amend
a színpadra állított fájlt rögzítjük! Ezután ismét megnyílik egy Vim ablak a commit üzenettel:
Módosíthatjuk a commit üzenetet, vagy hagyhatjuk úgy, ahogy van. Válasszuk azt, hogy a commit üzenetet változatlanul hagyjuk, és írjuk be a :wq
billentyűt a mentéshez és az ablakból való kilépéshez.
Már megszerkesztettük a régi commitunkat. És most mi lesz? Futtassuk a git status
:
Interaktív újraindítás folytatása
Nincs más változtatnivalónk a commitban, tehát folytassuk!
Futtassuk a git rebase --continue
és a következő üzenetet látjuk:
Woah, kész vagyunk? De mi van azzal a másik két commit-al? Nos, a következő commit, amire cselekedni kellett, az 6c01350
volt. Ezt a commitot törlésre jelöltük (drop
), amikor elindítottuk az interaktív újraindítást. A Git automatikusan törölte, és áttért a következő commitra, 41aa9d2
-re. Ezt a commitot nem módosítottuk a kezdeti interaktív újraindítás során. Az alapértelmezett parancsa pick
volt, ami azt jelenti, hogy a commitot használni fogjuk. A Git alkalmazta ezt a commitot, és mivel ez volt az utolsó commit, az interaktív újraindítás befejeződött.
Megjegyezzük, ha több commitunk lett volna, amit szerkeszteni kell, akkor egyszerűen áttértünk volna a következő commitra, és elkezdtük volna a módosítási folyamatot, ahogy fentebb tettük. A ciklus addig folytatódik, amíg nincs több commit.
A kilökés gomb
Azt érdemes megjegyezni, hogy ha az interaktív újraindításunk bármelyik pontján elrontunk valamit, és nem tudjuk, hogyan javítsuk ki, bármikor megszakíthatjuk. Bármelyik ponton lefuttathatjuk a git rebase --abort
parancsot a terminálban, és az interaktív rebase megszakad a változtatások mentése nélkül. Ekkor újra kell kezdenünk az interaktív újraindítást.
Az interaktív újraindítás után
A git naplónk most így néz ki:
Láthatod, hogy néhány dolog megváltozott az interaktív újraindítás megkezdése előttihez képest:
- Már nincs meg a
6c01350
commitunk a “Remove merge conflict” commit üzenettel. Ez az a commit, amelyet az interaktív újraalapozás során töröltünk. - Az általunk szerkesztett
4a4d705
commitunknak más SHA-1-je van,2b7443d
. - Az eredeti git naplóban szereplő legfrissebb commitunknak,
41aa9d2
-nek szintén új SHA-1-je van,2b95e92
. Ez a commit nem változott, hanem egyszerűen az előtte lévő2b7443d
.
Az interaktív újraszerkesztés mellékhatásai
A git naplónk két legfrissebb commitja esetében, mivel új SHA-1-ek vannak, a Git teljesen új commitoknak tekinti őket. Ez még az utolsó commitunkra, 2b95e92
is igaz, ahol sem a commit üzenet, sem a fájlok nem változtak egyáltalán. Ez felvet egy fontos pontot az interaktív újraszerkesztéssel kapcsolatban: Ha módosítunk egy commitot, annak a commitnak és az azt követő commitoknak új SHA-1-ek lesznek.
Ez nem befolyásol semmit, ha az általunk módosított commitok nem kerültek át egy távoli ágba. Ha azonban valóban elvégeztél egy interaktív rebase-t olyan commitokon, amelyeket már egy távoli ágba toltál, majd újra toltad az ágadat, akkor azt fogod látni:
Technikailag megkerülheted ezt a git push --force
használatával, de ez nagyon veszélyes. Ha a távoli ágon vannak commitok másoktól, de a helyi ágadon még nincsenek ilyen commitok, akkor gyakorlatilag törlöd az ő commitjaikat.
Egy másik megoldás a git push --force-with-lease
használata, ami csak a te commitjaidat módosítja, de a másokéit nem, bár ez is problémás lehet. Például, ha egy másik fejlesztő már rendelkezik azokkal a commitokkal, amelyek új SHA-1-eket kaptak a helyi ágán, akkor amikor a távoli ágat húzza, összeolvadási konfliktusai lesznek ezekkel a commitokkal.
Az, hogy mikor érdemes használni az --force-with-lease
-t, meghaladja ennek a blogbejegyzésnek a kereteit, de a legjobb lenne, ha konzultálnál a csapatod többi tagjával, mielőtt ezt tennéd. A git push --force-with-lease
-ról bővebben itt olvashatsz.
A legfontosabb tanulság ebből a szakaszból az, hogy sokkal egyszerűbb és biztonságosabb az interaktív újraszerkesztést használni olyan commitokon, amelyeket még nem tettek át egy távoli ágba.
Az írás szerzője Blake DeBoer. Eredetileg a Dev.to
Senior, Lead, or Principal developer in NYC? A Stride felvételt hirdet! Szeretnéd szintre emelni a tech csapatodat? Nézze meg, hogyan csináljuk! www.stridenyc.com
Tags
Létrehozza ingyenes fiókját, hogy feloldja az egyéni olvasási élményt.
Leave a Reply