Subversion
V kaptiole o verzování jste se dozvěděli co to jsou verzovací systémy a k čemu jsou dobré. V této kapitole popíšu jeden z nich – Subversion.
Vytvoření repozitáře
První, co musíte udělat, pokud chcete používat SVN, je vytvořit repozitář a nahrát do něj váš adresář. Tím vytvoříte první verzi.
Jako příklad projektu použiji zdrojové soubory k programu Známky a kredity (ver. 4.01) (je součástí zdrojových kódů). Po rozbalení zdrojových kódů uvidíte v adresáři 11subversion adresáře var/svn, Windows a znamky4.01.
Adresář var/svn budu používat pro uložení repozitářů. Normálně se v Linuxu
používá adresář /var/svn/
, ale repozitář můžete mít uložený
kdekoliv. (Já třeba ukládám svoje repozitáře do adaresáře
~/.svnRepository
.)
V adresáři znamky4.01 je uložený neverzovaný projekt (to se ale brzo změní). Adresář Windows představuje nějaký jiný počítač, kde budu pracovat s druhou kopijí projetku.
Krok číslo 1 je vytvoření repozitáře.
$ $ ls var/svn/znamky/
conf db format hooks locks README.txt
A to je celé. svnadmin
je program, který se používá
pro administraci repozitáře. Umí toho víc než jen vytvořit repozitář,
ale v tomto kurzu se sním už nesetkáte :-).
Co budete používat hlavně, je příkaz svn
.
Krokem číslo 2 bude vytvoření adresáře v rámci repozitáře, do kterého vložíte
projekt. K práci se soubory v repozitáři musíte používat přikaz
svn
. Soubory v repozitáři jsou totiž komprimované a navíc,
jak budete přidávat, měnit a odstraňovat soubory a adresáře, budou se
ukládat do repozitáře pouze změny (ne celý projekt). Příkazy svn jsou naštěstí
dost podobné příkazům linuxové příkazové řádky, takže si na ně rychle zvyknete.
Jak už jsem psal, k SVN můžete přistupovat lokálně, nebo přes internet.
Pokud přistupujete lokálně, musíte příkazu svn říct cestu k repozitáři
absolutní cestou, která začíná na file:///
.
Teď záleží na tom, kde máte uložený repozitář. Já si jeho obsah mohu vypsat
pomocí následujícího příkazu:
Tentokrát se nevypíše nic, protože ještě v repozitáři znamky nic není.
Vytvořím si tedy adresář trunk
.
Adresář trunk
se běžně používá pro název hlavní větve projektu.
O tom, co jsou to větve a k čemu jsou dobré bude řeč později. Teď mi věřte,
že trunk
je ten jediný správný název :-).
Committed revision 1.
$ svn ls file:///home/petr/resource/c/linux/zdrojaky-linux/11subversion/var/svn/znamky/
trunk/
Tadáá, máte svojí první verzi projektu. Text argumentu -m "..."
je
zpráva, která se uloží spolu s ukládanou verzí. Kdykoliv přidáváte nějakou novou
verzi, SVN po vás chce komentář. Pokud byste -m
neuvedli, otevře
se vám editor, do kterého můžete komentář zapsat (to se hodí pro delší, víceřádkové
komentáře).
Stažení projektu
Teď máte repozitář s projektem a s větví trunk
. Abyste
s projektem mohli pracovat, musíte si ho stáhnout do nějaké pracovní
kopie. K tomu se používá svn checkdout
.
Pracovních kopií si můžete udělat kolik chcete. Pro začátek udělám jednu. A udělám jí v adresáři znamky4.01. Za chvilku uvidíte proč.
Pro některé příkazy poskytuje svn zkratky, například místo
checkout
stačí napsat co
.
$ svn co file:///home/petr/resource/c/linux/zdrojaky-linux/11subversion/var/svn/znamky/trunk .
Checked out revision 1.
Všiměte si, že na konci cesty je trunk.
Příkaz svn co
má jako argument cestu k repozitáři a adresář, kam
se má trunk stáhnout. Tím je tečka, tj. aktuální adresář.
V aktuálním adresáři teď najdete adresář .svn
.
To je všechno, co odlišuje pracovní kopii SVN od neverzované kopie projektu.
entries format pristine tmp wc.db
Adresáře .svn a jeho obsahu si nemusíte více všímat.
Vložení souborů do projektu
Příkazem svn status
se můžete podívat na to, v jakém
stavu je váš projekt (předpokládám, že jste v adresáři pracovní kopie,
tj. v adresáři znamky4.01).
? Makefile
? create-gdbm.sh
? curses.c
? curses.h
? jmeno_adr.c
? lib.h
? lib_dbm.h
? main.c
? menu.c
? pbadresar.c
? statistika
? struktury.h
? struktury_dbm.h
? trideni
? trunk
? vpismena.c
? zaznam
? znamky
Příkaz vypsal všechny soubory, které se liší od poslední uložené verze/revize. Protože poslední revize je prázdný adresář (trunk), vypsali se všechny soubory. Otazník na začátku znamená „tento soubor neznám“.
Pro SVN neznámé soubory a adresáře označíte k verzování příkazem svn add
.
A create-gdbm.sh
A curses.c
A curses.h
A jmeno_adr.c
A lib_dbm.h
A lib.h
A main.c
A Makefile
A menu.c
A pbadresar.c
A statistika
A statistika/kreditu.c
A statistika/udelano.c
A statistika/prumer.c
A statistika/Makefile
A statistika/hranice25.c
A struktury_dbm.h
A struktury.h
A trideni
A trideni/trideni_vsemestru.c
A trideni/Makefile
A trideni/trideni_znamka.c
A trideni/trideni_semestr.c
A vpismena.c
A zaznam
A zaznam/smaz_zaznam.c
A zaznam/zaznam_novy.c
A zaznam/Makefile
A zaznam/zaznam_editace.c
A zaznam/zaznamenej.c
A zaznam/prepis.c
A zaznam/zjisti_info.c
A (bin) znamky
Z výpisu je vidět, že se přidali (A) všechny soubory, včteně souborů
v adresářích. Hvězdička v příkazu funguje tak, jak je v příkazovém
řádku obvyklé – nahrazuje všechny soubory. Můžete samozřejmě
přidávat jeden soubor za druhým jejich vyjmenováním, tj. něco jako
svn add create-gdbm.sh curses.c statistika …
.
Soubor znamky je binární soubor, tj. SVN v něm nedokáže
zobrazit změny řádek po řádce.
Je to zkompilovaný program, který jsem přidal do SVN omylem. Zkompilovaný
program verzovat nepotřebuji, tak ho smažu. Co nato SVN?
$ svn st znamky
!M znamky
SVN píše, že je něco v nepořádku (!) a že se soubor znamky změnil (M).
Smazání je taky změna :-). V nepořádku je proto, protože jsem ho smazal
příkazem rm
, a ne pomocí svn. To neva, to pořád moho
napravit.
D znamky
Prozatím jsem nic neodeslal do repozitáře, takže smazaný soubor znamky je navždy ztracen.
Podívejte se, jak by vypadalo, kdybych použil svn. V příkladu vytvořím prázdný soubor znamky (příkazem touch), přidám ho do SVN a zase smažu.
$ svn add znamky
A znamky
$ svn del znamky
svn: E195006: Use --force to override this restriction (local modifications may be lost)
svn: E195006:
'/home/petr/resource/c/linux/zdrojaky-linux/11subversion/znamky4.01/znamky' has local modifications -- commit or revert them first
A chyba je tu. SVN si stěžuje, že chci smazat soubor, který má lokální
modifikace (nový soubor se považuje za celý zmondifikovaný) a proto ho
odmítne smazat, dokud modifikace nepošlete do repozitáře. Když si ale jste
jistí, že modifikace chcete nadobro ztratit, můžete použít přepínač
--force
.
D znamky
A teď konečně odešlu všechno do repozitáře příkazem
svn commit
.
Adding Makefile
Adding create-gdbm.sh
...
Adding zaznam/zjisti_info.c
Transmitting file data .............................
Committed revision 2.
$ svn st
Hurá. Vytvořil jsem revizi 2. Jak vidíte, číslo revize stoupá při každé
změne v repozitáři (První revize byla vytvoření adresáře trunk).
Příkaz svn status
už nic nevypíše,
protože jsou teď všechny soubory v pracovním adresáři schodné s tím,
co je v repozitáři.
Práce se soubory
svn nabízí několik příkazů pro práci se soubory, které byste měli používat. Můžete je používat jak v pracovním adresáři, tak přímo v repozitory!
- svn del
- Smazání souboru. Ten už znáte.
- svn mkdir
- Vytvoření adresáře. Vzpomínáte na vytváření adresáře trunk?. To byl příklad použití příkazu přímo v repozitáři.
- svn copy
- Kopírování souborů. Subversion si bude pamatovat, že nový soubor pochází z toho původního (bude udržovat jeho historii). Pokud byste zkopírovali soubor bez svn a pak ho přidali do repozitáře, subversion by o tuto informaci přišlo.
- svn mv
- Přesun souborů a adresářů.
Řekněme, že se rozhodnu vytvořit soubor README. Něco do něj zapíšu a pošlu ho do repozitáře.
# neco do nej zapisuji
$ svn add README
A README
$ svn commit -m "Přidan sobor README"
Adding README
Transmitting file data .
Committed revision 3.
Teď jsem si ale vzpoměl, že by bylo lepší ho pojmenovat README.txt
A README.txt
D README
$ svn st
D README
> moved to README.txt
A + README.txt
> moved from README
Příkaz svn move
se tváří, jako by přidal README.txt a smazal
README, ale svn status
ho usvědčuje, že si i zapamatoval,
že soubor README.txt pochází z README (znak plus vedle A říká, že jde o
přidání nového soubor, který má ale navíc nějakou historii).
Deleting README
Adding README.txt
Committed revision 4.
Slučování změn
Teď ukáži, co se stane, když měníte jeden soubor v různých praconvích kopiích. Pro začátek si vytvořím novou pracovní kopii v adresáři Windows.
$ svn co file:///home/petr/resource/c/linux/zdrojaky-linux/11subversion/var/svn/znamky/trunk znamky
A znamky/curses.h
A znamky/lib.h
...
A znamky/menu.c
Checked out revision 4.
Stáhla se mi poslední verze projektu. Teď se rozhodnu upravit soubor statistika/kreditu.c a smazat z něj nepoužívanou proměnnou nacteno.
# edit statistika/kreditu.c
$ svn st
M statistika/kreditu.c
Vidíte, že je soubor modifikovaný (M). Co se v něm ale změnilo?
Na to vám odpoví příkaz svn diff
.
Index: statistika/kreditu.c
===================================================================
--- statistika/kreditu.c (revision 4)
+++ statistika/kreditu.c (working copy)
@@ -8,7 +8,6 @@
void
kreditu (DBM * dbm_ptr)
{
- struct zaznam nacteno;
struct dbm_info inf;
WINDOW *new_win;
wint_t ch;
Nechal jsem si vypsat všechny změny z adresáře statistika
.
Změněná je jen jedna řádka v jednom souboru. Řádka začíná mínusem, jako
že je smazaná. Kromě toho je vypsáno několik řádek nad a po, abyste se
lépe zorientovali.
@@ -8,7 +8,6 @@
říká, že výpis začíná na řádku 8 a zobrazuje 7 řádků
pro revizi 4, tj. tu z repozitáře a pro pracovní kopii (working copy) začíná také na
řádku 8, ale vypisuje jen 6 řádek (nepočítá se ta řádka s mínus).
Teď se ještě rozhodnu změnit něco v souboru README.txt. Podtrhnu nadpisy Popis a Instalace. Nadpis Instalace ještě odsadím o řádek.
$ svn diff README.txt
Index: README.txt
===================================================================
--- README.txt (revision 4)
+++ README.txt (working copy)
@@ -1,4 +1,5 @@
Popis
+.....
Tento program je určen (nejen) pro studenty vysokých škol. Ukáže Vám, jak
poctivě studujete. Zaznamenáte si do něj své předměty a on vám na oplátku
@@ -6,7 +7,9 @@
kreditů jste již získali za semestr.
Zvýrazňuje předměty, u nichž jste ještě zkoušku neudělali, můžete si
vyhledávat předměty dle názvu nebo kódu (viz. obrázek) atd.
+
Instalace
+.........
Program je vytvořen pro OS Linux a byl testován v distribuci Ubuntu a
OpenSuSE. Stačí jej rozbalit a spustit. Dodává se včetně zdrojových kódů,
Tentokrát jsem řádky jen přidával, takže vidíte jen řádky s plusem …
Je na čase práci uložit do repozitáře.
Sending README.txt
Sending statistika/kreditu.c
Transmitting file data ..
Committed revision 5.
$
Teď se přesunu do druhé pracovní kopie a rozhodnu se aktualizovat adresář statistika/
$ svn up statistika/
Updating 'statistika':
U statistika/kreditu.c
Updated to revision 5.
No vida, soubor statistika/kreditu.c se updatoval (U). (Neupdatoval se ale soubor README.txt, protože ten není v adresáři statistika.)
Konflikty
Protože jsem ale zapoměl, že jsem už nadpisy v README.txt podtrhal (nebo tu změnu udělal jakože nějaký můj kolega, co semnou na programu spolupracuje a já o ní nevím), udělám podtržení znovu. Místo teček ale podtrhnu nadpisy pomocí hvězdiček. Nadpis Instalace jsem také odsadil o jeden řádek.
$ svn st
M README.txt
$ svn commit -m "Podtrzeni nadpisu"
Sending README.txt
svn: E155011: Commit failed (details follow):
svn: E155011: File '/home/petr/resource/c/linux/zdrojaky-linux/11subversion/znamky4.01/README.txt'
is out of date
svn: E160028: File '/trunk/README.txt' is out of date
Ajaj, soubor se nepodařilo odeslat. Nemůžete poslat do repozitáře soubor,
který změnil už někdo jiný. Takže si nejdřív stáhnu aktuální verzi
z repozitáře pomocí svn update
.
Updating 'README.txt':
C README.txt
Updated to revision 5.
Conflict discovered in file 'README.txt'.
Select: (p) postpone, (df) show diff, (e) edit file, (m) merge,
(mc) my side of conflict, (tc) their side of conflict,
(s) show all options: p
$ Summary of conflicts:
Text conflicts: 1
$ svn st
C README.txt
? README.txt.mine
? README.txt.r4
? README.txt.r5
Summary of conflicts:
Text conflicts: 1
Ajaj, další problém. SVN zjistil konflikt. Tj změny, které jsem udělal
v README.txt a změny, které byli v repozitáři jsou na stené řádce
a SVN nedokáže rozhodnout, co z toho je platný. Dává mi na výběr několik
možností. Vybral jsem si p
jako postpone, tj. odložení řešení
problému na později.
Soubor README.txt je teď v konfliktu (C). Subversion vytvořil několik jeho kopií, README.txt.mine je kopie souboru, který jste měli v pracovní adresáři. README.txt.r4 je kopie souboru, který jste naposledy stáhli (tj vezre naposledy stažená do vašeho pracovního adresáře) a README.txt.r5, cože je kopie verze, kterou jste se snažili stáhnout teď.
Soubor README.txt obsahuje teď něco takového:
Popis <<<<<<< .mine ***** ======= ..... >>>>>>> .r5 Tento program je určen (nejen) pro studenty vysokých škol. Ukáže Vám, jak poctivě studujete. Zaznamenáte si do něj své předměty a on vám na oplátku spočítá vážený průměr, kolik trojek vám chybí do hranice 2.5 a kolik kreditů jste již získali za semestr. Zvýrazňuje předměty, u nichž jste ještě zkoušku neudělali, můžete si vyhledávat předměty dle názvu nebo kódu (viz. obrázek) atd. Instalace <<<<<<< .mine ********* ======= ......... >>>>>>> .r5 Program je …
Všechny řádky, které nedokázal svn sloužit jsou označeny pomocí <<<<<<< a >>>>>>>.
Po >>>>>>> .mine
následují konfliktní řádky (v příkladu jen
jeden řádek s hvězdičkama), pak =======
,
pak řádky z revize, kterou jsem se snažil aktualizovat a pak
>>>>>>> .r5
.
Teď je na mě, abych upravil soubor do stavu, který mi vyhovuje. Řekněme, že chci ponechat podtržení s hvězdičkami, tak všechno výše zmíněné smažu a nechám jen hvězdičky.
$ svn diff README.txt
Index: README.txt
===================================================================
--- README.txt (revision 5)
+++ README.txt (working copy)
@@ -1,5 +1,5 @@
Popis
-=====
+*****
Tento program je určen (nejen) pro studenty vysokých škol. Ukáže Vám, jak
poctivě studujete. Zaznamenáte si do něj své předměty a on vám na oplátku
@@ -9,7 +9,7 @@
vyhledávat předměty dle názvu nebo kódu (viz. obrázek) atd.
Instalace
-=========
+*********
Program ...
README.txt je ale stále ve stavu konfliktu, tak musím svn říct,
že už jsem problém vyřešil (příkazem svn resolved
).
C README.txt
? README.txt.mine
? README.txt.r4
? README.txt.r5
Summary of conflicts:
Text conflicts: 1
$ svn resolved README.txt
Resolved conflicted state of 'README.txt'
$ svn st
M README.txt
$ svn commit -m "Změna podtržení z teček na hvězdičky"
Sending README.txt
Transmitting file data .
Committed revision 6.
Cestování časem
Příkaz svn log
zobrazí uložené revize s popisem.
S přepínačem -v
zobrazí i soubory, keré se změnili.
------------------------------------------------------------------------
r1 | petr | 2014-08-22 10:56:47 +0200 (Pá, 22 srp 2014) | 1 line
Changed paths:
A /trunk
Zalozeni vetve trunk
------------------------------------------------------------------------
Ale co to? Že bych měl jen jednu revizi? Subversion umožňuje, abyste měli v pracovní kopii různé verze souborů. Proto se po odeslání (commitu) automaticky nestáhne nejnovější verze celého adresáře. Takže je to potřeba udělat ručně.
Updating '.':
At revision 6.
Zdánlivě se nic nestalo (nezměnil se žádný soubor), ale teď už je celý
pracovní adresář v revizi 6 a podle toho se bude chovat i svn
log
. Parametrem -l 3
jsem omezil výpis
na poslední 3 revize.
------------------------------------------------------------------------
r6 | petr | 2014-08-22 10:56:51 +0200 (Pá, 22 srp 2014) | 1 line
Changed paths:
M /trunk/README.txt
Změna podtržení z teček na hvězdičky
------------------------------------------------------------------------
r5 | petr | 2014-08-22 10:56:50 +0200 (Pá, 22 srp 2014) | 1 line
Changed paths:
M /trunk/README.txt
M /trunk/statistika/kreditu.c
Podtržení nadpisů v README.txt a smazání nepoužité proměnné
------------------------------------------------------------------------
r4 | petr | 2014-08-22 10:56:49 +0200 (Pá, 22 srp 2014) | 1 line
Changed paths:
D /trunk/README
A /trunk/README.txt (from /trunk/README:3)
Přejmenování README na README.txt
Za domácí úkol vyzkoušejte svn log -v README.txt
.
Hádejte, zobrazí se vám i historie souboru README
,
ze kterého README.txt
vzešel? Následující příklad
napoví.
Další cestování v čase umožňuje příkaz svn diff
.
Můžete si zobrazit rozdíl v souborech v libovolných verzích.
Index: README
===================================================================
--- README (.../README) (revision 3)
+++ README (.../README.txt) (revision 6)
@@ -1,9 +1,12 @@
Popis
+*****
Tento program je určen (nejen) pro studenty vysokých škol. Ukáže Vám,
jak poctivě studujete. Zaznamenáte si do něj své předměty a on vám na
oplátku spočítá vážený průměr, kolik trojek vám chybí do hranice 2.5 a
kolik kreditů jste již získali za semestr.
Zvýrazňuje předměty, u nichž jste ještě zkoušku neudělali, můžete si
vyhledávat předměty dle názvu nebo kódu (viz. obrázek) atd.
+
Instalace
+*********
Program je vytvořen pro OS Linux a byl testován v distribuci Ubuntu a
OpenSuSE. Stačí jej rozbalit a spustit. Dodává se včetně zdrojových kódů,
takže si jej můžete i přeložit.
Nechal jsem si zobrazit rozdíl mezi 3 a 6 verzí. Z výpisu vidíte, že verze 6 má oproti verzi 3 navíc podtržené nadpisy hvězdičkami. Mezi těmito verzemi je ještě verze s podtržením tečkami, ale já chtěl jen rozdíl verzí 3 a 6.
A nejlepší na konec. Příkazem svn up
s volbou
-r
si mohu stáhnou z repozitáře libovolnou verzi
dokumentu, nebo i celého adresáře. Jak vypadal můj projekt po druhém
commitu?
Updating '.':
D README.txt
U statistika/kreditu.c
Updated to revision 2.
Soubor README.txt tehdy ještě neexistoval (ani README). Vrátili se i změny provedené v souboru statistika/kreditu.c. A teď zase z5 na aktuální verzi.
Updating '.':
A README.txt
U statistika/kreditu.c
Updated to revision 6.
Větve (branches) a tagy
Teď už umíte všechno co je potřeba k tomu, abyste mohli subversion používat. Pokud ale chcete, můžete číst dále :-).
Už víte, že si můžete zkopírovat celý projekt do jiného adresáře v repozitáři. Tím vytvoříte tzv. větev (branch). K čemu je to dobré? Můžete pracovat v této jiné větvi na nějakém úkolu, aniž byste ovlivnili hlavní větev (trunk). Na hlavní větvi mezi tím může váš kolega provádět jiné změny, aniž byste mu narušoval práci svými změnami. Pokud se vám změny líbí, můžete je snadno sloučit do hlavní větve (merge). Pokud se vám nelíbí, prostě větev smažete.
Než ukážu typický proces větvení, ještě se zmíním o tagování. Tag se používá k nějakému lidskému označení revize. Když se rozhodnete zveřejnit novou verzi svého programu, většinou ho nějak pojmenujete a dáte mu číslo verze (ale asi jiné, než používá subversion).
Subversion žádný speciální nástroj pro tagování nemá, místo toho
existuje taková „nepsaná“ dohoda, že se tagování provádí
kopií projektu do adresáře tags
.
Subversion vytváří tzv. levné kopie. Když mu řeknete, že má (v repozitáři) vytvořit kopii, subversion si jenom poznamená z které verze kopie vychází a jak se jmenuje. Není vůbec důvod, aby fyzicky data zkopíroval, takže taková levná kopie nezabírá skoro žádné místo.
Větve, ve kterých chcete něco měnit, se ukládají do adresáře
branches
. Jedná se zase o „nepsanou“ dohodu,
ale rozhodně doporučuji se tohoto postupu držet. Některé nástroje,
které umí s SVN pracovat, na tento způsob pojmenování větví a tagů spoléhá.
Committed revision 7.
$ svn mkdir ^/tags -m "Adresář pro tagování"
Committed revision 8.
Teď si otaguji aktuální větev. Je na čase vydat verzi znamky4.02 :-) Kopii můžu udělat rovnou v repozitáři.
Protože jsem v adresáři znamky4.01, mohu si dovolit použít
zkrácený zápis k repozitáři pomocí stříšky ^
.
Stříška se nahradí plnou cestou k repozitáři
file:///home/petr/resource/c/linux/zdrojaky-linux/11subversion/var/svn/znamky/
.
Committed revision 9.
$ svn ls ^/
branches/
tags/
trunk/
$ svn ls ^/tags
znamky4.02/
^/tags/znamky4.02/ je vlastně také větev. Ale tuto větev byste už nikdy neměli měnit. Je tu přece jako odraz stavu toho, co jste zveřejnili lidem.
Teď budu pokračovat ve vývoji hlavní větve (trunk), kterou mám pořád
v pracovní kopii. Upravím například soubor Makefile, aby příkazy
rm
měli argument -f
a v souboru
curses.h
změním knihovnu ze staré
<curses.h> na novou <ncurses/curses.h>. A změny odešlu
do SVN.
$ svn st
M Makefile
M curses.h
$ svn commit -m "Vylepšní makefile a změna knihovny cures na ncurses"
Sending Makefile
Sending curses.h
Transmitting file data ..
Committed revision 10.
Ale moment! Teď mi došlo, že jsem zapoměl změnit číslo verze v souborech README.txt a struktury.h, takže ve verzi 4.02 je pořád zapsáno 4.01. Jak už jsem psal, jednou vydaná verze by se neměla měnit. Jako že jsem ale naštěstí ještě nic nezveřejnil, takže si to můžu dovolit.
Potřebuju nějak upravit větev ^tags/znamky4.02
.
Mohou si ji pomocí svn checkout
celou stáhnout,
ale mám i lepší možnost – pomocí svn switch
se do ní „přepnout“.
Příkazem svn info
se pak můžete podívat,
s jakou větví pracujete.
U curses.h
U Makefile
Updated to revision 10.
$ svn info
Path: .
Working Copy Root Path: /home/petr/resource/c/linux/zdrojaky-linux/11subversion/znamky4.01
URL: file:///home/petr/resource/c/linux/zdrojaky-linux/11subversion/var/svn/znamky/tags/znamky4.02
Relative URL: ^/tags/znamky4.02
Repository Root: file:///home/petr/resource/c/linux/zdrojaky-linux/11subversion/var/svn/znamky
Repository UUID: 36c47b24-bcaa-4063-9b01-284b1bcfb08a
Revision: 10
Node Kind: directory
Schedule: normal
Last Changed Author: petr
Last Changed Rev: 9
Last Changed Date: 2014-08-22 11:30:35 +0200 (Pá, 22 srp 2014)
$
znamky
).
Tak jednoduché a rychlé to bylo! Jen 2 soubory se změnili a už pracuji v jiné větvi :-).
Teď provedu požadované změny a odešlu je.
$ svn commit -m "Změna čísla verze z 4.01 na 4.02"
Sending README.txt
Sending struktury.h
Transmitting file data ..
Committed revision 11.
Tak mě napadlo, co kdybych, ještě než 4.02 zveřejním, přenesl změny z hlavní větve? Není problém, trochu si zamergeujeme …
svn: E195020: Cannot merge into mixed-revision working copy [10:11]; try updating first
Nojo, zase jsem neupdatoval a tak mám soubory v různé verzi
(viz svn st- v
). To se dá snadno napravit.
10 9 petr .
10 2 petr Makefile
11 11 petr README.txt
10 2 petr create-gdbm.sh
10 2 petr curses.c
...
10 2 petr statistika/udelano.c
11 11 petr struktury.h
10 2 petr struktury_dbm.h
...
$ svn up
Updating '.':
At revision 11.
$ svn st -v
11 11 petr .
11 2 petr Makefile
11 11 petr README.txt
11 2 petr create-gdbm.sh
11 2 petr curses.c
...
11 2 petr statistika/udelano.c
11 11 petr struktury.h
11 2 petr struktury_dbm.h
...
První sloupec ukazuje aktuální číslo verze v pracovním adresáři, druhý sloupec ukazuje číslo verze, kdy se soubor naposledy změnil (přesněji řečeno, o jaké poslední změně ví váš pracovní adresář).
--- Merging r9 through r11 into '.':
U Makefile
U curses.h
--- Recording mergeinfo for merge of r9 through r11 into '.':
U .
Subversion ví, v jaké revizi se větev znamky4.02 oddělila od větve trunk a přenese změny od tohoto okamžiku (r9) až k té poslední (r11). Navíc zapíše do adresáře (.) informaci o provedeném merge, takže při příštím merge přenese změny od r11 dále. Změny se teď zapsali do vaší pracovní kopie, takže je ještě potřeba poslat je na server.
M .
M Makefile
M curses.h
$ svn commit -m "Merge změn z trunk"
Sending .
Sending Makefile
Sending curses.h
Transmitting file data ..
Committed revision 12.
Teď se můžu vrátit zpět k větvi trunk
.
U struktury.h
U README.txt
U .
Updated to revision 12.
Tak mě napadlo, nešlo by přenést změny z znamky4.01 do trunk? Jasně že šlo. A navíc chci přenést jen změnu s číslem verzí. To taky není problém.
------------------------------------------------------------------------
r12 | petr | 2014-08-22 12:04:12 +0200 (Pá, 22 srp 2014) | 1 line
Merge změn z trunk
------------------------------------------------------------------------
r11 | petr | 2014-08-22 11:53:17 +0200 (Pá, 22 srp 2014) | 1 line
Změna čísla verze z 4.01 na 4.02
------------------------------------------------------------------------
r9 | petr | 2014-08-22 11:30:35 +0200 (Pá, 22 srp 2014) | 1 line
Verze 4.02
------------------------------------------------------------------------
Z výpisu se dočtu, že mě zajímá rozdíl mezi revizí 9 a 11.
--- Merging r10 through r11 into '.':
U struktury.h
U README.txt
--- Recording mergeinfo for merge of r10 through r11 into '.':
U .
Příkazy svn st
a svn diff
si můžete prohlédnout
mergnuté změny a pak je odeslat příkazem svn commit
. To už vám
nechám za domácí úkol.
Celý proces větvení a mergování z této kapitoly jsem se pokusil znázornil na obrázku:
Pamatujte, že větve pro práci byste měli dělat v adresáři branches. To, že jsem ukazoval příklady s větví v tags, bylo jen kvůli zkrácení výukového textu.
Tak jste viděli, jak pracovat s větvemi, jak mezi nimi přepínat a jak přenášet změny z jedné větve do druhé.
Máte už docela slušné základy SVN, ale je toho pořád hodně co nevíte.
Nevíte třeba, jak označit některé soubory, aby je SVN ignorovalo (a neverzovalo).
Nevíte, jak pracovat se repozitářem na jiném stroji (přes HTTP nebo SSH) a nevíte
spoustu dalších drobností.
Všechno si můžete nastudovat na svnbook.red-bean.com/. Můžete také použít
příkaz svn help
pro zobrazení nápovědy.
Doufám, že od teď už budou všechny vaše projekty pod dohledem nějakého
verzovacím systému.
Ve zdrojových kódech ke stažení máte všechny příkazy z této kapitoly uloženy v souboru Makefile. Což je, myslím, hezká ukázka toho, jak lze využít Makefile také na něco jiného, než jen překlad zdrojového kódu.