Vladimír Mach @vladimirmach 29.1 0. 2012
Agenda Konflikty v rámci jednoho souboru Konflikty v rámci struktury adresáře (tree conflicts) Shallow checkout
Flag Význam U Updated Soubor byl aktualizován o změny ze serveru G Merged Lokální a vzdálené změny byly sloučeny automaticky C Conflict Konflikt v souboru, který je nutno vyřešit D Deleted Soubor byl v repozitáři odstraněn A Added Soubor byl nově v repozitáři vytvořen
konfliktu Možnost Slovo Význam e Edit show all changes made to merged file df Diff-full show all changes made to merged file r Resolved accept merged version of file dc Display-conflict show all conflicts (ignoring merged version) mc Mine-conflict accept my version for all conflicts (same) tc Theirs-conflict accept their version for all conflicts (same) mf Mine-full accept my version of entire file (even non-conflicts) tf Theirs-full accept their version of entire file (same) p Postpone mark the conflict to be resolved later l Launch launch external tool to resolve conflict Pokud rovnou víme, že konflikt nechceme řešit hned: svn update --non-interactive
Zobrazení konfliktů (df) display-full Vypíše seznam všech rozdílů mezi lokální a vzdálenou verzí (dc) display-conflict Vypíše jen ty konflikty, které se nepodařilo vyřešit automaticky
Možnosti řešení (e) edit Otevření editoru podle proměnné EDITOR (r) resolved Po provedení změn potvrdí aktuální verzi a označí konflikt jako vyřešený (mc) mine-conflict Odmítnutí všech konfliktních změn ze serveru, ale nekonfliktní pasáže ze serveru akceptuje (tc) their-conflict Zahození lokálních konfliktních změn, ale zachová všechny lokální nekonfliktní pasáže
Možnosti řešení (2) (mf) mine full Zahodí všechny změny ze serveru a zachová lokální verzi (tf) theirs full Zahodí všechny lokální změny a přepíše je změnami ze serveru
Připomenutí: označení revizí HEAD Nejaktuálnější verze repozitáře BASE Číslo revize v naší working copy, pokud soubor byl upraven, tak k souboru před úpravami COMMITTED Nejaktuálnější revize předcházející nebo rovna BASE, ve které byl soubor změněn PREV Předcházející revize revizi kdy byl soubor změněn. Odpovídá to COMMITTED-1 Příklad: svn diff -r PREV:COMMITTED foo.c ukáže poslední commitované změny souboru foo.c
Odložené řešení (p) postpone Nechá soubor v konfliktním stavu k pozdějšímu vyřešení Soubor zůstane označen flagem C Na disku se vytvoří 3 dočasné neverzované soubory file.mime File.rOLD File.rNEW Námi upravený soubor před aktualizace repozitáře Původní neupravovaná verze souboru před aktualizací repozitáře (BASE) Nová verze souboru přijatá po aktualizaci repozitáře (HEAD) Subversion může do souborů umístit tzv. conflict markers Viditelné oddělení konfliktních oblastí Určuje se podle MIME typu souboru Dokud tyto soubory nebudou odstraněny, (přes svn resolve) nebude možné provést commit # svn commit svn: Commit failed (details follow): svn: Aborting commit: 'file' remains in conflict
Odložené řešení (2) Conflict markers <<<<<<< filename naše změny ======= kód z repozitáře >>>>>>> revision Po provedení změn označíme konfliktní soubor jako uzavřený Pomocí svn resolve
Odložené řešení svn resolve Pro vyřešení použijeme parametr --accept hodnota base mine-full theirs-full working Význam Výběr verze, kterou jsme naposledy checkoutovali před provedenými změnami Výběr verze, která obsahuje pouze naše změny Výběr verze, která obsahuje pouze změny ze serveru a tedy zahození všech našich změn Výběr verze, kterou jsme ručně upravili (projitím a úpravou conflict markers v souboru) # svn resolve --accept working SOUBOR Resolved conflicted state of 'SOUBOR'
Tree conflicts
Tree conflicts Konflikty, které nastávají při přejmenování nebo odstranění souborů Například při refaktorování kódu může jeden vývojář rozdělit soubor na více souborů, ale my provedli změny na původním velkém Před verzí 1.6 se toto chování nijak neřešilo mohly se nějaké lokální upravy ztratit. Pokud situace nastala, tak: Se zkontroloval soubor jestli nebyl modifikován, Smazal se na původním umístění a pokud byl modifikován, tak se zachoval, ale už jako neverzovaný, Přidal se soubor, tak jak je ve vzdáleném repozitáři na nové umístění. Od verze 1.6 se toto už označí jako konflikt, který musí být vyřešen
Řešení Připomenutí: SVN přesun souboru chápe jako zkopírování + odstranění Přejmenování souboru jiným přispěvovatelem během našich úprav Commit selže (svn status nám oznámí flagem C konflikt) Z commit logu zjistíme, že soubor byl přejmenován SVN automaticky označí tento smazaný soubor zpět k přidání Už nám ale neřekne, jestli soubor byl opravdu smazán, nebo přejmenován -> odhadnout ze zprávy v commit logu S přejmenováním souhlasíme, takže náš soubor smažeme, ale předtím musíme ručně změny přenést do nově přijatého z repozitáře Buď opravdu ručně, nebo pomocí patch souborů
Demo Dvě working copy 2 vývojářů Přejmenování souboru s třídou, aby odpovídalo jménu třídy v souboru # svn cp Rights.php Acl.php # svn rm Rights.php # svn commit -m "Renamed file to same name as class inside." 1 2 Přidání nových oprávnění do původního souboru # svn commit -m "Add new role with corresponding rights." Sending models/rights.php svn: Commit failed (details follow): svn: File 'Rights.php' is out of date svn: File not found: transaction '3-3', path '/trunk/app/models/rights.php'
Demo Aktualizujeme si tedy repozitář a podíváme se co se změnilo # svn update C Acl.php A Rights.php Updated to revision 3. Summary of conflicts: Tree conflicts: 1 Pomocí svn status se podíváme detailněji na podrobnosti # svn status A + C Acl.php > local edit, incoming delete upon update M Rights.php Podíváme se tedy do logu co se v repozitáři změnilo # svn log --verbose -r3 ------------------------------------------------------------------------ r3 vlada 2012-10-28 05:57:07 +0100 (Sun, 28 Oct 2012) 1 line Changed paths: D /trunk/app/models/rights.php A /trunk/app/models/acl.php (from /trunk/app/models/rights.php:2) 2 Renamed file to set filename same as class name.
Demo Pomocí svn info se podíváme detailněji na konflikt # svn info Acl.php tail -n 4 Tree conflict: local edit, incoming delete upon update Source left: (file) http://server/svn/nette/trunk/app/models/acl.php@2 Source right: (none) http://server/svn/nette/trunk/app/models/acl.php@3 2 Left URL říká lokální zdroj konfliktu, right URL říká zdroj příchozího konfliktu, podle těchto cest víme kde hledat problém Když znovu zkusíme commit # svn commit -m "Add new role with corresponding rights." svn: Commit failed (details follow): svn: Aborting commit: '/tmp/mff/demo2/app/models/acl.php' remains in conflict 2 Provedené změny tedy musíme přenést do nového souboru
Demo Vytvoříme si patch soubor se změnami # svn diff Rights.php > PATCH Upravíme výskyty Rights.php za Acl.php # svn patch PATCH U Acl.php 2 Nyní už jen vyřešíme konflikt # svn delete --force Rights.php D Rights.php # svn resolve --accept=working Rights.php Resolved conflicted state of 'Rights.php Nyní už můžeme provést commit # svn commit -m "Add new role with corresponding rights." Sending models/acl.php Transmitting file data. Committed revision 4.
Shallow checkouts
Nerekurzivní/s omezenou hloubkou checkout z repozitáře Výhodné pokud máme jeden společný repozitář s několika projekty, ale chceme lokálně načíst jen nějakou podmnožinu projektů # svn checkout --depth empty http://svnserver/solution/ solution # svn update --set-depth infinity project1/trunk # svn update --set-depth infinity project2/trunk
http://svnbook.red-bean.com/en/1.7/svn.tour.cycle.html#svn.tour.cycle.resolve http://svnbook.red-bean.com/en/1.7/svn.tour.revs.specifiers.html http://svnbook.red-bean.com/en/1.7/svn.tour.treeconflicts.html http://www.tomred.net/svn-shallow-checkouts.html