Изменения

Сравнение DVCS - несколько задач

1992 байта добавлено, 19:01, 18 ноября 2009
Нет описания правки
== Работа с SVN (миграция и синхронизация) ==
 
Что любопытно — с Subversion-репозиториями DVCS работают, как правило, гораздо быстрее самого Subversion, и быстрее всех работает '''Bazaar'''. То есть, в принципе, можно вообще жить с Subversion-сервером и Bazaar-клиентом.
'''Mercurial''': отлично! Есть несколько расширений — [http://mercurial.selenic.com/wiki/HgSubversion hgsubversion], [http://pypi.python.org/pypi/hgsvn hgsvn], [http://mercurial.selenic.com/wiki/ConvertExtension convert], позволяющих работать с Subversion тем или иным образом, и не совместимых друг с другом. Самое вменяемое из них — '''hgsubversion''', хотя и заявлено, что оно ещё сырое, и, к сожалению, не распространяется вместе с Mercurial’ом. Имеет фактически весь необходимый функционал — можно делать и <tt>push</tt>, и <tt>pull</tt> в/из Subversion, можно клонировать SVN-репозиторий с сохранением веток и меток (правда, обязательно стандартное их расположение в корневых поддиректориях <tt>/trunk</tt>, <tt>/branches</tt>, <tt>/tags</tt>), эти два метода совместимы, <tt>rebase</tt> также работает, а граф ветвлений сохраняется. Очень крут тот факт, что ветка, которая создавалась неполным копированием <tt>trunk</tt>'а, то есть, копированием некоторых его поддиректорий, успешно подцепилась в нужное место графа ветвлений. Ни Bazaar, ни Git этого не смогли.
'''Git''': очень хорошо (5-)! <tt>[http://git-svn.yhbt.net/ git-svn]</tt> встроен в git и умеет всё, что нужно: клонирование, синхронизация (<tt>fetch</tt>, <tt>pull</tt> или <tt>merge</tt>), фиксация изменений в Subversion-репозиториях (<tt>dcommit</tt>) и <tt>rebase</tt> работают с сохранением веток и меток, причём стандартная схема их именования <tt>trunk/branches/tags</tt> не является обязательной. Ветки SVN импортируются как [http://www.gitready.com/beginner/2009/03/09/remote-tracking-branches.html Remote Tracking Branches], что тоже удобно — можно начинать историю ветки в git’е не с сотворения миров, а с любого момента. Также <tt>git-svn</tt> поддерживает подключаемые внешние репозитории Subversion (т. н. [http://svnbook.red-bean.com/en/1.0/ch07s03.html Externals]). Граф ветвлений сохраняется, хоть и не так круто, как в Mercurial’е. В общем, функционал фактически полон.
'''Bazaar''': очень хорошо! . Можно импортировать репозиторий командами <tt>svn-import</tt> или <tt>branch</tt>, можно делать <tt>push</tt> и <tt>pull</tt> в/из Subversion. При импорте можно сохранить все ветки и метки в одном хранилище (если использовать [http://bazaar-vcs.org/SharedRepositoryTutorial Shared Repository]), для этого также требуются стандартные названия <tt>trunk/branches/tags</tt>. Граф ветвлений Subversion сохраняется, но также не отражает копирования подпапок. Также существует несколько других расширений для импорта Subversion в Bazaar, но они хуже.
Между прочимИ всё было бы замечательно, но есть любопытная одна очень неприятная проблема. Причём возникающая в достаточно простой ситуации. То есть пусть бы она и была, если забыть обновить но в очень редкой ситуации — это можно терпеть. Но тут ситуация довольно частая. Так вот. Всё начинается с обычной ситуации — мы сделали изменение в '''Bazaar'''-клонированном SVN-ветку перед внесением изменений… репозитории, а кто-то тем временем сделал изменение '''в самом SVN-репозитории'''… Причём не важно, в каких файлах: даже если конфликтов в наших изменениях нет, ситуация возникает всё равно. Что нам теперь остаётся делать? Ну конечно, мержиться. И merge успешно проходит. Но в случае отсутствия конфликтов'''Bazaar''' помните — после этого merge нужно сразу делать rebase и push в Subversion! Иначе, если до этого сделать ещё хотя бы один commit в Bazaar, push не удастся, а rebase не поможет или вывалится с исключением. Хотите подробнее? Рассмотрим следующую последовательность действий:
# Клонируем svn в ветку bzr1.
# Делаем pull из svn в ветку bzr1 — bzr1 снова синхронизирован с svn.
# <strike>Делаем push из bzr2 в bzr1 — облом: ветки «разошлись»</strike>. Хорошо, делаем merge из bzr1 в bzr2. Коммитим (фиксируем).
# (Необязательно, но так интереснееважно) Снова вносим изменения в bzr2, коммитим.
# Теперь хотим протащить изменения из bzr2 в svn. Сначала делаем push из bzr2 в bzr1. Теперь история bzr1 идентична истории bzr2.
#: <font color="red">'''И это не так тривиально, как хотелось бы!'''</font>
#: Потому что теперь импортированные из svn в bzr1 ревизии ''заменяются одной merge-ревизией'', а после неё в истории появляется ревизия с модификацией, импортированная из bzr2. Исходные svn-ревизии «подцепляются» к merge-ревизии. Чтобы увидеть их, нужно сказать не просто <tt>bzr log</tt>, а <tt>bzr log -n0</tt>.
# <strike>Делаем push из bzr1 в svn — облом: в bzr1 есть ревизия, «воткнутая» между уже зафиксированными в репозитории svn-ревизиями</strike>.  И что теперь делать?#: <pre>bzr: ERROR: Operation denied because it would change the mainline history. Set the append_revisions_only setting to False on branch "..." to allow the mainline to change.</pre>#: Bazaar предлагает нам разрешить менять местами ревизии в SVN-репозитории, а . Но если разрешить — всё равно обламывается (ну кто ж тебе по [[rupedia:WebDAV|WebDAV]] даст ревизии местами переставить, даа) и предлагает использовать rebase. А rebase — и это из-за пункта 7 — нам не поможет, а скажет «no revisions to rebase». А в некоторых комбинациях — вывалится со змеиным исключением.# Чтобы исправить эту ситуацию, клонируем : # Клонируем svn ещё раз в ветку bzrtmp.
# Делаем merge из bzr1 в bzrtmp, коммитим. Теперь в bzrtmp последней ревизией будет merge-ревизия, к которой «подцеплены» ревизии, которые мы так жаждем протащить-таки в SVN.
# Теперь мы можем сделать push из bzrtmp в svn, а потом из svn — pull во все остальные ветки, и они придут к согласованному виду…
Что ещё любопытно — с SubversionХотите автоматический скрипт? Пожалуйста: [[Файл:bzr-репозиториями DVCS работают, как правило, гораздо быстрее самого Subversionrebase-dont-help.sh]]. В результате последней команды bzr скажет «<tt>ERROR: exceptions.AttributeError: 'NoneType' object has no attribute 'get_known_graph_ancestry'</tt>», уйдёт в Python Traceback и быстрее всех работает оттуда не вернётся. А в '''BazaarMercurial'''. То есть, в принципе, можно вообще жить с Subversionточно такой же ситуации rebase замечательная работает. Пример аналогичного скрипта: [[Файл:hg-сервером и Bazaarrebase-клиентомbetter-than-bzr-ithelps.sh]].
== Управление патчами ==