Децентрализированная модель разработки Mercurial'а может несколько озадачить новых пользователей. Эта статья предназначена для иллюстрации основных концепций и объяснения её принципов с большей наглядностью. Для пошаговых инструкций - смотрите [[Tutorial]]. ''(Translations: [[BrazilianPortugueseUnderstandingMercurial|Brazilian Portuguese]], [[ChineseUnderstandingMercurial|Chinese]], [[FrenchUnderstandingMercurial|French]], [[GermanUnderstandingMercurial|German]], [[ItalianUnderstandingMercurial|Italian]], [[JapaneseUnderstandingMercurial|Japanese]], [[KoreanUnderstandingMercurial|Korean]], [[RussianUnderstandingMercurial|Russian]], [[SpanishUnderstandingMercurial|Spanish]] )'' <> == Что такое репозиторий == [[Repository|Репозиторий]] Mercurial'а содержит [[WorkingDirectory|рабочие директории]] с своей "памятью": {{{#!dot digraph G { compound=true; rankdir = LR background="#999999"; subgraph cluster_1 { style=filled; color="#eeeeee"; node [shape=box,style=filled,color=lightgray]; "ревизия 0" -> "ревизия 1" -> "ревизия 2" -> "ревизия 3"; label = "память"; } subgraph cluster_0 { style=filled; color=lightgrey; node [style=filled,color=white]; edge [style=invis]; "main.c"-> "main.h" -> ".hgignore" -> ".hgtags" label="рабочая директория"; } "ревизия 2" -> ".hgtags" [lhead = cluster_0 constraint=false] } }}} Это память содержит '''полную''' историю проекта. В отличие от традиционной SCMs, где есть только одна центральная копия истории, каждая рабочая директория содержит свою собственную копию истории. Это позволяет распараллелить разработку. Рабочая директория содержит копию файлов проекта в определенное время (например, ревизии 2), готовых к редактированию. Поскольку [[Tag|теги]] и проигнорированные файлы тоже подконтрольны ревизии, они так же включены в копию. == Коммит изменений == Когда вы делаете [[Commit|коммит]], состояние рабочей директории по отношению к её [[Parent|родителям]] записывается как новая [[Revision|ревизия]]: {{{#!dot digraph G { compound=true; rankdir = LR background="#999999"; subgraph cluster_1 { style=filled; color="#eeeeee"; node [shape=box,style=filled,color=lightgray]; "ревизия 0" -> "ревизия 1" -> "ревизия 2" -> "ревизия 3"; "ревизия 2" -> "ревизия 4"; label = "память"; } subgraph cluster_0 { style=filled; color=lightgrey; node [style=filled,color=white]; edge [style=invis]; "main.c"-> "main.h" -> ".hgignore" -> ".hgtags" label="рабочая директория"; } "ревизия 2" -> ".hgtags" [style = dotted lhead = cluster_0 constraint=false] "ревизия 4" -> ".hgtags" [lhead = cluster_0 constraint=false] ".hgtags" -> "ревизия 4" [color = red label = "commit" ltail = cluster_0 constraint=false] } }}} Отметьте, что ревизия 4 - это '''[[Branch|ветка]]''' ревизии 2, которая, в свою очередь, была ревизией рабочей директории. Теперь ревизия 4 - '''родитель''' рабочей директории. == Ревизии, Наборы изменений(Changesets), Вершины(Heads), и Tip == Mercurial группирует связанные изменения разных файлов в единые атомарные [[ChangeSet|Наборы изменений]]([[ChangeSet|changesets]]), которые являются ревизиями целого проекта. Каждый из них имеет последовательный [[RevisionNumber|номер ревизии]]. Из-за того, что Mercurial допускает распределенную параллельную разработку, номера ревизий могут быть несогласованы между пользователями. Поэтому Mercurial также присваивает каждой ревизии глобальный [[ChangeSetID|ID набора изменений]]. Идентификаторы наборов изменений являются 40-разрядными 16-ричными числами, но могут быть сокращены до любого однозначного префикса, например, "e38487". {{{#!dot digraph { rankdir = LR node [shape=box] "rev 0:838e" -> "rev 1:34ef" -> "rev 2:4563" "rev 1:34ef" -> "rev 3:fe56" "rev 2:4563" -> "rev 4:ac98" "rev 3:fe56" -> "rev 4:ac98" "rev 4:ac98" -> "rev 5:0345" "rev 4:ac98" -> "rev 6:19e3 (tip)" label="пример истории" } }}} Ветки и [[Merge|слияния]] в истории ревизий могут появляться в любой момент. Каждая неслитая ветка создает новую [[Head|вершину]] в истории ревизий. Здесь ревизии 5 и 6 являются вершинами. Mercurial рассматривает ревизию 6 как [[Tip|наконечник (tip)]] хранилища (вершину с наибольшим номером ревизии). == Клонирование, Внесение изменений, Слияние, и Pulling == Давайте начнем с пользователем Алиса, которая имеет хранилище выглядящее так: {{{#!dot digraph { label="Хранилище Алисы" rankdir = LR node [shape=box] a->b->c->d } }}} Боб [[Clone|клонирует]] это хранилище и в итоге получает полную копию хранилища Алисы (хотя его рабочая директория независима!): {{{#!dot digraph { label="Хранилище Боба" rankdir = LR node [shape=box] a->b->c->d } }}} Затем Боб [[Commit|коммитит]] некоторые изменения: {{{#!dot digraph { label="Хранилище Боба" rankdir = LR node [shape=box] a->b->c->d->e->f e [color=blue] f [color=blue] } }}} Алиса затем параллельно вносит свое собственное изменение: {{{#!dot digraph { label="Хранилище Алисы" rankdir = LR node [shape=box] a->b->c->d->g g [color=red] } }}} Боб затем [[Pull|вытягивает(pulls)]] хранилище Алисы для синхронизации. Это копирует все изменения Алисы в хранилище Боба: {{{#!dot digraph { label="Хранилище Боба" rankdir = LR node [shape=box] a->b->c->d->e->f e [color=blue] f [color=blue] d->g g [color=red;label="g (tip)"] } }}} Из-за того, что ревизия '''g''' Алисы является новейшей вершиной в хранилище Боба, теперь она является '''конечной ревизией''' ('''tip'''). Затем Боб производит [[Merge|слияние]], которое объединяет последнее изменение, над которым он работал ('''f'''), с конечным изменением (tip), подтверждает (commit) результат и в итоге получает: {{{#!dot digraph { label="Хранилище Боба" rankdir = LR node [shape=box] a->b->c->d->e->f e [color=blue] f [color=blue] d->g g [color=red] f->h g->h h [color=green;label="h (tip)"] } }}} Теперь, если Алиса '''вытянет изменения''' ('''pulls''') от Боба, она получит изменения Боба e, f, и h, и они будут полностью синхронизованы: {{{#!dot digraph { label="Хранилище Алисы" rankdir = LR node [shape=box] a->b->c->d->g d->e->f e [color=blue] f [color=blue] g [color=red] f->h g->h h [color=green;label="h (tip)"] } }}} == Децентрализованная система == Mercurial полностью децентрализованная система, и поэтому не имеет внутреннего понятия о центральном хранилище. Поэтому пользователи вольны определять свои собственные топологии для разделения изменений (см. CommunicatingChanges): {{{#!dot digraph { Алиса -> Центральное Центральное -> Алиса Боб -> Центральное Алиса -> Боб Алиса -> Карл Карл -> Центральное Боб -> Карл Карл -> Боб "Лаптоп Карла" -> Карл Карл -> "Лаптоп Карла" "Лаптоп Карла" -> Центральное Центральное [style=fill;color=blue;label="Main Public Repo"] label="Сеть Mercurial" } }}} == Чего не может Mercurial == Знакомые с SVN/CVS пользователи ожидают, что с помощью hg можно размещать и раздельно использовать несколько проектов в одном репозитории. В действительности, это не то, ради чего hg был создан, и тут нужно пробовать другие варианты организации работы. В частности, это означает, что вы не можете получить из репозитория только один каталог. Если вам никак не обойтись без управления несколькими проектами через некий вариант мета-репозитория, вы можете попробовать использовать ForestExtension. Пошаговую инструкцию по использованию Mercurial смотрите в [[Tutorial]]. ---- CategoryRussian