Настало время перейти от абстракций к конкретике. В этом разделе мы покажем реальные примеры использования Subversion.
Вы уже читали о рабочих копиях; теперь мы покажем как Subversion-клиент создает и использует их.
Рабочая копия Subversion представляет собой обычное дерево каталогов на вашем компьютере, содержащее набор файлов. Вы можете по-своему усмотрению редактировать эти файлы и, если это исходные коды, вы можете обычным способом скомпилировать программу. Ваша рабочая копия это ваше личное рабочее пространство: Subversion как не смешивает вносимые другими изменения с вашими, так и не делает доступными для других изменения сделанные вами, пока вы не прикажете сделать это. Вы даже можете иметь несколько рабочих копий одного и того же проекта.
После того, как вы внесли изменения в файлы вашей рабочей копии и убедились в том, что они корректно работают, Subversion предлагает вам команды «публикации» (записи в хранилище) ваших изменений, в результате чего они станут доступными для всех участников проекта. Если другие участники проекта опубликовали свои изменения, Subversion предлагает вам команды для объединения (путем чтения информации из хранилища) этих изменений с вашей рабочей копией.
Рабочая копия содержит несколько дополнительных файлов, созданных и обслуживаемых Subversion, которые помогают ей при выполнении этих команд. В частности, каждый каталог в вашей рабочей копии содержит подкаталог с именем .svn который называется служебным каталогом рабочей копии. Файлы в служебном каталоге помогают Subversion определить какие файлы рабочей копии содержат неопубликованные изменения, и какие файлы устарели по отношению к файлам других участников.
Как правило, хранилище Subversion содержит файлы (или исходный код) нескольких проектов; обычно каждый проект представляется в виде подкаталога файловой системы хранилища. При таком подходе, пользовательская рабочая копия обычно соответствует отдельному подкаталогу хранилища.
Например, предположим, что у вас есть хранилище, содержащее два программных проекта: paint и calc. Каждый проект располагается в своем собственном каталоге, как показано на Рисунок 2.6, «Файловая система хранилища».
Рисунок 2.6. Файловая система хранилища
Для того чтобы создать рабочую копию, вам нужно получить какую-либо из подкаталогов хранилища. (Возможно, термин получить звучит как что-то связанное с блокированием или резервированием ресурсов, но это не так; эта команда просто создает для вас личную копию проекта.) Например, если вы получите /calc, у вас будет рабочая копия, наподобие этой:
$ svn checkout http://svn.example.com/repos/calc
A calc/Makefile
A calc/integer.c
A calc/button.c
Checked out revision 56.
$ ls -A calc
Makefile integer.c button.c .svn/
Буквы А говорят о том, что Subversion добавил этот элемент в вашу рабочую копию. Теперь у вас есть личная копия каталога /calc хранилища, с одним небольшим добавлением — каталогом .svn, содержащим, как было указано выше, дополнительную информацию, необходимую Subversion.
URL хранилища
Получить доступ к хранилищу Subversion можно различными способами — на локальном диске или через ряд сетевых протоколов. Местоположение хранилища всегда определяется при помощи URL. Таблица Таблица 2.1, «URL для доступа к хранилищу.» показывает соответствие разных URL-схем возможным методам доступа.
Таблица 2.1. URL для доступа к хранилищу.
Схема
|
Метод доступа
|
file:///
|
прямой доступ к хранилищу (на локальном диске)
|
http://
|
доступ через протокол WebDAV (если Subversion-сервер работает через Apache)
|
https://
|
тоже что и http:// но с SSL-шифрованием
|
svn://
|
доступ через собственный протокол к серверу svnserve
|
svn+ssh://
|
тоже что и svn://, но через SSH-соединение
|
Подробнее о том, как Subversion обрабатывает URL, см. в «Subversion Repository URLs».
Предположим, вы внесли изменения в button.c. Так как каталог .svn помнит дату изменения файла и его оригинальное содержимое, Subversion может сказать о том, что вы изменили файл. Subversion не публикует ваших изменений пока вы не прикажете это сделать. Публикация ваших изменений более известна как фиксация (или checking in) изменений в хранилище.
Для того, что бы опубликовать ваши изменения вы можете воспользоваться командой commit:
$ svn commit button.c
Sending button.c
Transmitting file data .
Committed revision 57.
Теперь ваши изменения в button.c зафиксированы в хранилище; если другой пользователь создаст рабочую копию /calc, он увидит ваши изменения в последней версии файла.
Предположим, у вас есть партнер, Салли, которая создала рабочую копию /calc одновременно с вами. Когда вы зафиксировали изменения в button.c, рабочая копия Салли осталась не измененной; Subversion модифицирует рабочие копии только по запросу пользователей.
Для приведения рабочей копии в актуальное состояние, Салли может попросить Subversion обновить её рабочую копию, используя команду Subversion update. Это внедрит ваши изменения в ее рабочую копию вместе с другими изменениями, которые были зафиксированы с момента когда она создавала рабочую копию.
$ pwd
/home/sally/calc
$ ls -A
.svn/ Makefile integer.c button.c
$ svn update
U button.c
Updated to revision 57.
Вывод команды svn update говорит, что Subversion обновила содержимое button.c. Обратите внимание, что Салли не должна указывать, какой файл обновить; для определения файлов, которые необходимо привести в актуальное состояние, Subversion использует информацию в каталоге .svn, а также информацию из хранилища.
Правки
Операция svn commit может опубликовать изменения любого количества файлов и каталогов за одну атомарную операцию. В своей рабочей копии вы можете менять содержимое файлов, создавать, удалять, переименовывать и копировать файлы и каталоги, а затем зафиксировать все изменения за один раз.
В хранилище каждая фиксация отражается как атомарная операция: либо изменения вносятся полностью, либо не вносятся вообще. Subversion ведёт себя так, принимая в расчет возможные сбои в программах, системные сбои, проблемы с сетью, а также неверные действия пользователя.
Каждый раз, когда происходит фиксация, создаётся новое состояние файловой системы, которое называется правка. Каждая правка получает уникальный номер, на единицу больший номера предыдущей правки. Начальная правка только что созданного хранилища получает номер 0 и не содержит ничего, кроме пустого корневого каталога.
Рисунок 2.7, «Хранилище» отлично иллюстрирует хранилище. Представьте массив номеров правок, начинающийся с 0, с направлением слева направо. Каждый номер правки имеет соответствующее дерево файлов, а каждое дерево представляет собой «снимок» того, как хранилище выглядело после фиксации.
Рисунок 2.7. Хранилище
Глобальные номера правок
В отличие от многих других систем управления версиями, номера правок в Subversion относятся ко всем, а не только к отдельно взятым файлам. Каждый номер правки соответствует целому дереву, отдельному состоянию хранилища после зафиксированного изменения. Иначе говоря — правка N представляет состояние файловой системы хранилища после выполнения N-ой фиксации. Когда пользователи Subversion говорят о «правке 5 foo.c », на самом деле речь идет о « foo.c входящем в правку 5». Заметьте, что обычно правки N и M файла не обязательно будут отличаться. Поскольку в CVS используется пофайловая нумерация правок, пользователи CVS могут обратиться за более подробной информацией к Приложение A, Subversion для пользователей CVS.
Важно помнить то, что рабочие копии не всегда соответствуют какой-то одной правке в хранилище; они могут содержать файлы из разных правок. Например, вы получили рабочую копию из хранилища, у которого самая последняя правка — 4:
calc/Makefile:4
integer.c:4
button.c:4
На данный момент рабочий каталог полностью соответствует правке 4 в хранилище. Допустим, что вы внесли изменения в button.c, и зафиксировали эти изменения. При отсутствии других фиксаций ваша фиксация создаст правку под номером 5, и теперь ваша рабочая копия выглядит следующим образом:
calc/Makefile:4
integer.c:4
button.c:5
Предположим, что после этого Салли фиксирует изменения integer.c, создавая правку 6. Если вы воспользуетесь svn update для приведения своей рабочей копии в актуальное состояние, то она станет выглядеть так:
calc/Makefile:6
integer.c:6
button.c:6
Изменения, внесенные Салли в integer.c будут отражены в вашей рабочей копии, и ваши изменения в button.c также будут присутствовать. В этом примере текст Makefile в правках 4, 5 и 6 идентичен, однако, Subversion проставляет номер правки 6 для вашей рабочей копии Makefile, чтобы показать что файл не устарел. Таким образом, после того как вы выполните полное обновление вашей рабочей копии, она будет полностью соответствовать текущему состоянию хранилища.
Как рабочие копии отслеживают хранилище
В служебном каталоге .svn/ для каждого файла рабочего каталога Subversion записывает информацию о двух важнейших свойствах:
-
на какой правке основан ваш рабочий файл (это называется рабочая правка файла), и
-
временной (ударение на последний слог) метке, определяющей, когда рабочая копия последний раз обновлялась из хранилища.
Используя эту информацию при соединении с хранилищем, Subversion может сказать, в каком из следующих четырех состояний находится рабочий файл:
Не изменялся и не устарел
Файл не изменялся в рабочем каталоге, в хранилище не фиксировались изменения этого файла со времени создания его рабочей правки. Команды svn commit и svn update никаких операций делать не будут.
Изменялся локально и не устарел
Файл был изменен в рабочей копии, но в хранилище не фиксировались изменения этого файла после правки, на которой он основан. Есть локальные изменения, которые не были зафиксированы в хранилище, поэтому svn commit выполнит фиксацию ваших изменений, а svn update не сделает ничего.
Не изменялся и устарел
В рабочем каталоге файл не изменялся, но был изменен в хранилище. Необходимо выполнить обновление файла для того, чтобы он соответствовал текущей правке. Команда svn commit не сделает ничего, а svn update обновит вашу рабочую копию файла в соответствии с последними изменениями.
Изменялся локально и устарел
Файл был изменен как в рабочем каталоге, так и в хранилище. svn commit потерпит неудачу, выдав ошибку «out-of-date». Файл необходимо сначала обновить; svn update попытается объединить локальные изменения с опубликованными. Если Subversion не сможет самостоятельно совершить объединение, он предложит пользователю разрешить конфликт вручную.
Может показаться, что следить за актуальным состоянием рабочей копии сложно. Это не так. Для того, чтобы узнать состояние любого элемента в вашей рабочей копии существует команда svn status. За более подробной информацией об этой команде обратитесь к «svn status».
Смешивание правок в рабочих копиях
Subversion старается быть гибкой настолько, насколько это возможно. Например, существует возможность иметь рабочую копию, содержащую файлы и каталоги, имеющие смешанные номера рабочих правок. Но, к сожалению, эта гибкость иногда смущает некоторых новых пользователей. Если раньше примеры, показывающие смешанные правки, вызывали у вас чувство растерянности, то это руководство, которое рассказывает для чего такая возможность существует и как ее использовать, для вас.
Обновления и фиксации отделены друг от друга
Одно из фундаментальных правил Subversion заключается в том, что «передающее» действие не приводит к «принимаемому», и наоборот. То, что вы готовы внести изменения в хранилище, не означает то, что вы готовы принять изменения от других. А если вы все еще работаете над новыми изменениями, то svn update изящно объединит изменения из хранилища с вашими собственными, вместо того, что бы заставлять вас опубликовать их.
Главным побочным эффектом этого правила является то, что рабочая копия должна вести дополнительный учет при смешивании правок и быть аккуратной при любом смешивании. И то, что каталоги попадают под контроль версий, делает это еще более сложным для понимания.
Допустим, у вас есть рабочая копия, полностью соответствующая правке 10. После изменения файла foo.html, вы выполняете команду svn commit, которая создает в хранилище правку 15. После выполнения фиксации большая часть новичков ожидают, что вся рабочая копия будет иметь правку 15, однако это не так. Между правками 10 и 15 в хранилище могло быть внесено любое количество изменений. Так как команда svn update не выполнялась, а svn commit не загружает изменений, клиент ничего не знает о находящихся в хранилище изменениях. С другой стороны, если команда svn commit будет автоматически загружать последние изменения, то всей рабочей копии можно будет назначить соответствующий номер правки - 15. Однако нарушится фундаментальное правило, согласно которому «передача» и «получение» являются независимыми операциями. Следовательно, все, что может сделать клиент Subversion, это пометить один файл — foo.html — как соответствующий правке 15. Остальная рабочая копия продолжает соответствовать правке 10. Только при выполнении svn update будут загружены последние изменения и вся рабочая копия будет помечена как соответствующая правке 15.
Смешивание правок — это нормально
Фактически, каждый раз при выполнении svn commit правки рабочей копии смешиваются. Только что зафиксированные элементы отмечаются как имеющие больший номер рабочей правки, чем все остальные. После нескольких фиксаций (без выполнения обновлений между ними) правки рабочей копии будут полностью перемешаны. Даже если вы являетесь единственным пользователем хранилища, вы все равно с этим столкнетесь. Для просмотра этой смеси рабочих правок воспользуйтесь командой svn status --verbose (см. «svn status»).
Часто новые пользователи даже не подозревают о том, что их рабочая копия содержит смешанные правки. Это может сбить с толку, так как многие команды клиента чувствительны к рабочей правке элемента, с которым он работает. Например, команда svn log используется для вывода истории изменения файла или каталога (см. «svn log»). Когда пользователь вызывает эту команду применительно к объекту рабочей копии, он ожидает увидеть полную историю этого объекта. Однако если рабочая правка объекта очень старая (из-за того, что команда svn update долго не выполнялась) будет показана история для более старой версии этого объекта.
Смешивание правок — это полезно
Если у вас очень большой проект, вы можете найти полезным, время от времени принудительно «возвращать» части рабочей копии к более ранним правкам; как это делается, вы узнаете в Главе 3. Возможно вы захотите протестировать более раннюю версию модуля, находящегося в подкаталоге или точно узнать, когда в конкретном файле появилась ошибка. Это — «машина времени» — тот аспект системы управления версиями, который позволяет перемещать в истории любую часть рабочей копии вперед и назад.
Смешивание правок имеет ограничения
Несмотря на то, что в рабочей копии можно использовать смешивание правок, у этой гибкости существуют ограничения.
Во-первых, нельзя зафиксировать удаление устаревшего файла или каталога. Если в хранилище существует более новая версия элемента, попытка удаления будет отклонена для предотвращения возможности непреднамеренного уничтожения изменений о которых вы не в курсе.
Во-вторых, нельзя зафиксировать изменение метаданных для не обновленного каталога. О присвоении «свойств» к элементам вы узнаете в Главе 6. Рабочая правка каталога определяет конкретный набор входящих в нее элементов и свойств, поэтому фиксация изменений свойств для устаревшего каталога может привести к уничтожению свойств о которых вы не знаете.
Достарыңызбен бөлісу: |