Lekce 8 - Git - Slučování větví
V minulé lekci, Git - Správa větví, jsme se zabývali větvením.
V Git tutoriálu se budeme zabývat slučováním větví. Probereme si typy sloučení fast-forward merge a 3-way merge, které si vyzkoušíme na našem repozitáři.
Všechny příkazy si budeme opět zkoušet v našem
naklonovaném repozitáři laravel
z lekce Git - Základy -
Dokončení. Otevřeme terminál MinTTY
a pomocí příkazu
cd laravel
se do repozitáře přesuneme.
Slučování větví
Pro slučování větví máme v Gitu příkaz git merge
, který
slouží k integraci změn z jedné větve do jiné, čímž se spojí historie
obou větví. Tento proces je nezbytný zejména při spolupráci v týmu, kdy
různí členové pracují na různých větvích projektu a později se musí
jejich práce sloučit do hlavního kódu.
Při použití příkazu git merge <název_větve>
se
obsah a změny ze slučované větve začlení do cílové větve. Git se
snaží provést sloučení automaticky, pokud nedochází ke
konfliktům v kódu. Pokud však konflikty nastanou, Git
upozorní uživatele, jemuž umožní problémy ručně vyřešit.
Konflikty ve větvích se budeme zabývat dále v kurzu.
Po provedení sloučení se provedené změny ze slučované větve objeví v
cílové větvi jako nové commity, které zaznamenají historii sloučení. Na
následujícím obrázku vidíme, jak se změní cílová větev
main
po sloučení s větví feature
:

Před sloučením větví je třeba potvrdit přijímající větev a načíst nejnovější vzdálené commity.
Potvrzení přijímající větve
Před sloučením dvou větví je důležité zjistit, zda se nacházíme na
správné větvi, do které bude sloučení provedeno. Příkazem
git status
zjistíme, zda HEAD
ukazuje na správnou
větev přijímající sloučení. Pokud se nacházíme na špatné větvi,
použijeme příkaz git checkout <název větve>
pro změnu
větve.
Načtení nejnovějších vzdálených commitů
Dále se musíme ujistit, že cílová a slučovací větev obsahují
nejnovější commity. Pro aktualizaci větví spustíme příkaz
git fetch
, čímž si stáhneme nejnovější vzdálené commity.
Po dokončení načítání se příkazem git pull
ujistíme, že
cílová větev má nejnovější aktualizace.
Typy sloučení
V Gitu existují dva základní typy sloučení, které se používají k integraci změn z jedné větve do druhé. Jedná se o fast-forward merge a 3-way merge.
Fast-forward merge
Pokud commity cílové větve nejsou novější než commity větve slučované, pak použijeme právě fast-forward merge sloučení. Historie cílové větve se jednoduše posune dopředu na poslední commit ze slučované větve. To znamená, že se změny provedené ve slučované větvi přidají přímo na konec cílové větve.
Fast-forward merge sloučení můžeme použít v případě neexistence změn v cílové větvi od doby, kdy jsme se od ní odštěpili do slučované větve.
Na obrázku vidíme stav větvě main
a feature
před sloučením:

Po fast-forward merge budou větve vypadat následovně:

Příklad
Na následujícím příkladu si ukážeme sloučení dvou větví pomocí
fast-forward merge sloučení. Nejdříve se přepneme zpět do
větve 10.x
:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (3.0) $ git checkout 10.x ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $
Vytvoříme si novou testovací cílovou větev, do které budeme slučovat jinou větev:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $ git checkout -b test Switched to a new branch 'test' ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (test) $
Poté vytvoříme budoucí slučovanou větev feature
. Do
souboru README.md
přidáme text Přidaný text 1
.
Změny v souboru README.md
přidáme do staging area a commitneme.
Pak do souboru README.md
přidáme další nový text
Přidaný text 2
a podobně použijeme příkazy
git add
a git commit
:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $ git checkout -b feature ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ echo "Přidaný text 1" >> README.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git add README.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git commit -m "Edit souboru README.md" [feature 06db22b6] Edit souboru README.md 1 file changed, 1 insertion(+) ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ echo "Přidaný text 2" >> README.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git add README.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git commit -m "Dokončení úprav souboru README.md" [feature 3e638736] Dokončení úprav souboru README.md 1 file changed, 1 insertion(+) ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $
Pracovní prostory včetně staging area jsme probírali v lekci Git - Historie a principy.
Nyní provedeme sloučení větve feature
do cílové větve
test
pomocí fast-forward merge sloučení:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git checkout test ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (test) $ git merge feature Updating 7fe97a16..46736b9c Fast-forward README.md | 2 ++ 1 file changed, 2 insertions(+) ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (test) $
Následující výpis změn nám značí, kde došlo ke změnám při sloučení:
MINGW64:/c/mujgit/laravel Updating 7fe97a16..46736b9c Fast-forward README.md | 2 ++ 1 file changed, 2 insertions(+)
Nakonec větev feature
vymažeme:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (test) $ git branch -d feature Deleted branch feature (was 3e638736). ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (test) $
Tímto jsme úspěšně provedli sloučení dvou větví do jedné pomocí sloučení typu fast-forward merge. Toto sloučení však není možné, pokud se větve rozcházejí. Jestliže k cílové větvi neexistuje lineární cesta, Git nemá jinou možnost než větve zkombinovat pomocí 3-way merge sloučení.
3-way merge
Pokud jsou commity cílové větve novější než commity větve slučované, pak použijeme 3-way merge sloučení. Toto sloučení využijeme v případě, že se obě větve od okamžiku rozvětvení rozvíjely:

Během tohoto procesu Git automaticky detekuje, které části kódu byly upraveny na obou větvích od posledního společného commitu, a snaží se je sloučit do jednoho nového commitu. Pokud se v souborech nacházejí konflikty, Git tato místa označí a uživatelé musí tyto problémy ručně vyřešit. Tento proces je trochu složitější než u fast-forward merge, protože vyžaduje manuální zásahy a kontrolu konfliktů.
Po 3-way merge sloučení budou větve vypadat následovně:

Příklad
Na následujícím příkladu si ukážeme proces sloučení dvou větví
pomocí 3-way merge sloučení. Máme cílovou větev
10.x
, od které se odštěpíme do budoucí slučované větve
feature
. V této větvi pak pracujeme. Mezitím však náš kolega
vytváří změny v cílové větvi 10.x
.
Tento scénář se často vyskytuje při implementaci rozsáhlých funkcí nebo při současné práci několika vývojářů na jednom projektu.
Začneme přesunem do cílové větve 10.x
a vytvořením nové
budoucí slučované větve feature
:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (test) $ git checkout 10.x ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $ git checkout -b feature Switched to a new branch 'feature' ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $
Nyní pracujeme v naší větvi feature
. Do souboru
README.md
podobně přidáme nové texty a každou změnu přidáme
do staging area i lokálního
repozitáře:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ echo "Přidaný text 1" >> README.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git add README.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git commit -m "Úprava souboru README.md" [feature 7eebb0fa] Úprava souboru README.md 1 file changed, 1 insertion(+) ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ echo "Přidaný text 2" >> README.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git add README.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git commit -m "Dokončení úprav souboru README.md" [feature bd2e74b7] Dokončení úprav souboru README.md 1 file changed, 1 insertion(+) ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $
Nyní budeme simulovat současnou práci našeho kolegy v cílové větvi
10.x
. Do souboru CHANGELOG.md
vložíme text
Přidaný text do souboru
a změnu přidáme do staging
area i lokálního repozitáře:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (feature) $ git checkout 10.x ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $ echo "Přidaný text do souboru" >> CHANGELOG.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $ git add CHANGELOG.md ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $ git commit -m "Editace souboru CHANGELOG.md" [10.x 91276a86] Editace souboru CHANGELOG.md 1 file changed, 1 insertion(+) ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $
Nyní provedeme sloučení větve feature
do cílové větve
10.x
:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $ git merge feature
Otevře se nám slučovací soubor. Do něj bychom mohli přidat
odůvodnění sloučení větví. My tento soubor jen zavřeme stiskem klávesy
Esc. Poté napíšeme příkaz :wq
, čímž soubor
uložíme a ukončíme editor. Vypíše se nám následující zpráva o
provedených změnách sloučení:
MINGW64:/c/mujgit/laravel ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $ git merge feature Merge made by the 'ort' strategy. README.md | 2 ++ 1 file changed, 2 insertions(+) ItNetwork@DESKTOP-ADEVTG4 MINGW64 /c/mujgit/laravel (10.x) $
Tímto jsme pomocí 3-way merge úspěšně sloučili větev
feature
do větve 10.x
.
V následujícím kvízu, Kvíz - Zkoumání historie, správa a slučování větví v Gitu, si vyzkoušíme nabyté zkušenosti z předchozích lekcí.