Git
- decentralizovaný
- nelineární
- inkrementální ukládání změn
Workflow
git clone <url>
– naklonování existujícího repozitářegit init
– vytvoření prázdného repozitářegit status
– zobrazení stavu lokálního repozitářegit diff
– zobrazení rozdílu mezi lokálními soubory a posledním commitemgit log
,git log -p
– zobrazení historie commitůgit config --local user.name ...
,git config --local user.email ...
– konfigurace jména a adresy před vytvářením commitů
Přidávání změn:
git add
– přidat soubory do „zásobníku“ změn pro následující commitgit add -p
– interaktivní přidávání změn (lze přidat jen některé soubory nebo i část změn v daném souboru pro lepší logické členění změn do commitů)
git restore <file>
– zahození necommitovaných změngit reset <file>
nebogit restore --staged <file>
– vrátígit add
git mv <file_old> <file_new>
– přejmenování souborugit rm <file>
– smazání souborugit commit -m <message>
– vytvoření commitugit push
,git pull
– synchronizace lokálních změn se serverem
Pojmy
- repozitář
- commit
- větev
- remote
- head, HEAD
- ref – pojmenované odkazy, např. head, HEAD, remote, tag
- stash
A spousta dalších, viz https://git-scm.com/docs/gitglossary
Soubor .gitignore
- komentáře začínají znakem
#
- každý řádek obsahuje název souboru/adresáře, který chceme ignorovat
- lze používat
*
pro napasování libovolného řetězce (např.*.backup
zahrnuje všechny soubory končící řetězcem „.backup“)
Branching, merging, rebase
git checkout
– přepínání stavu souborů v adresáři dle zadaného stavu v gitugit checkout <commit_id>
– přesun na zadaný commit (libovolný přesun v historii,HEAD
bude odkazovat na<commit_id>
)git checkout <branch>
– přepínání mezi větvemi,HEAD
bude odkazovat na<branch>
git checkout <path/to/file>
– zahození lokálních změn v souboru/adresáři, přepsání stavem dle aktuálníHEAD
(ekvivalentní s příkazemgit restore <path/to/file>
)
git checkout -b <branch>
– vytvoření nové větve dle aktuálníHEAD
git merge <branch>
– sloučí zadanou větev do aktuální větve (viz obrázek)- commity ze zúčastněných větví jsou ve výsledném logu seřazeny chronologicky – není hned jasné, ve které větvi vznikly
- může dojít ke konfliktům – ty musí vyřešit uživatel, git je uloží v dodatečném commitu na konci větve (tzv. „merge commit“)
- z pohledu na merge commmit nemusí být hned patrné, jak byly které konflikty řešeny a které commity je způsobily
- zdůraznit, že
git merge
nelinearizuje historii (každý commit má pořád stejného předchůdce a následníka) – pouze v logu to tak vypadá
git rebase <branch>
– znovu aplikuje commity z aktuální větve, aby počátek („base“) této větve byl na zadané větvi (viz obrázek)- dojde k logickému uspořádání commitů (linearizace historie)
- při aplikaci každého commitu je potřeba potenciálně řešit konflikty způsobené právě tímto commitem – více práce pro uživatele, ale vede to k čistší a přehlednější historii změn
- po rebase lze provést merge bez konfliktů (a bez vytvoření dodatečného commitu) – tzv. fast forward, dojde k prostému přesunu např.
refs/heads/master
git rebase --interactive
, přepisování historie
Odkazy
Rebase:
- A rebase-based workflow
- Why is rebase-then-merge better than just merge (complement)
- Introduction to Git rebase, force-push, and merge conflicts
- Git Branching - Rebasing
Workflow, best practices: