Hg Init: Исправляем ошибки. Часть 4.

<html> <div class="content">

<img src="http://habrastorage.org/storage/eebea7f1/5482efc4/01467053/55589e0f.png" align="left">Это четвертая часть из серии <b>Hg Init: Учебное пособие по Mercurial</b> от Джоэля Спольски (<a href="http://www.joelonsoftware.com/">Joel Spolsky</a>). Предыдущие части:<br>

<ul> <li><a href="http://docs.mirocow.com/doku.php?id=hg_init:%D1%87%D0%B0%D1%81%D1%82%D1%8C_1._%D0%BF%D0%B5%D1%80%D0%B5%D0%BE%D0%B1%D1%83%D1%87%D0%B5%D0%BD%D0%B8%D0%B5_%D0%B4%D0%BB%D1%8F_%D0%BF%D0%BE%D0%BB%D1%8C%D0%B7%D0%BE%D0%B2%D0%B0%D1%82%D0%B5%D0%BB%D0%B5%D0%B9_subversion">«Переобучение для пользователей Subversion»</a></li> <li><a href="http://docs.mirocow.com/doku.php?id=hg_init:%D1%87%D0%B0%D1%81%D1%82%D1%8C_2._%D0%BE%D1%81%D0%BD%D0%BE%D0%B2%D1%8B_mercurial">«Основы Mercurial»</a></li> <li><a href="http://docs.mirocow.com/doku.php?id=hg_init:%D1%87%D0%B0%D1%81%D1%82%D1%8C_3._%D0%BE%D1%81%D0%BD%D0%BE%D0%B2%D1%8B_mercurial">«Привыкаем работать в команде»</a></li> </ul><br> <br> Одно из главных преимуществ Mercurial состоит в том, что вы можете использовать личные клоны репозитория для экспериментов и разработки новых возможностей. Если что-то пошло не так, можно все исправить за мгновение.<br> <br> <h4>Часть 4. Исправляем ошибки</h4><br> <br> <img src="http://habrastorage.org/storage/6fd42c43/97dcbec7/981c68fc/c68c9abb.png" align="left"><br> Mercurial позволяет свободно экспериментировать. Представьте, что во время работы вы что-то не то сделали в редакторе, и случилось нечто ужасное:<br> <br> <a name="habracut"></a><br> <br> <img src="http://habrastorage.org/storage/ca13ab4d/255dd0bc/0bb0ae94/924be9f7.png"><br> <br> Emacs, как же я тебя люблю. Как бы то ни было, все можно исправить. Наиболее распространённым способом справиться с такими проблемами является использование команды

hg revert

:<br> <br> <img src="http://habrastorage.org/storage/64abc0c1/6b548170/8fb06654/8d15fb91.png"><br> <br> <blockquote>

hg revert

<br> возвращает файлы к состоянию, зафиксированному в репозитории.<br> </blockquote><br> <br> Эта команда вернет файлы в именно то состояние, что было у них в момент последнего коммита. Mercurial не любит что-либо удалять, так что вместо того чтобы затереть рецепт на <a href="http://ru.wikipedia.org/wiki/%D0%9F%D0%BE%D1%80%D0%BE%D1%81%D1%8F%D1%87%D1%8C%D1%8F_%D0%BB%D0%B0%D1%82%D1%8B%D0%BD%D1%8C">свинском латинском</a>, он переименовал файл:<br> <br> <img src="http://habrastorage.org/storage/6bd1f78e/ff44c2ff/2af58601/3d594470.png"><br> <br> А что если все зашло слишком далеко и вы уже закоммитили?<br> <br> <img src="http://habrastorage.org/storage/9de936e9/28f4c3ef/539275c3/d981bd2d.png"><br> <br> Есть команда

hg rollback

, которая спасет вашу шкуру, но только если вы еще не протолкнули (push) ошибочный коммит в другой репозиторий. Эта команда отменяет <i>один</i> коммит.<br> <br> <img src="http://habrastorage.org/storage/25fdbb00/217ac772/0e6e63d8/beaa92be.png"><br> <br> <blockquote>

hg rollback

<br> отменяет один коммит, при условии, что вы не протолкнули его в другой репозиторий.<br> </blockquote><br> <br> Представьте, что вы хотите поставить большой эксперимент в свободное время. Ваш босс нанял нового дизайнера, Джима. С тех пор дизайны, которые вы получаете, стали просто абсурдны. В них кислотный зеленый текст, ничего не выровнено (на это есть «художественные» причины, ага) и юзабилити хромает. Вы хотите прийти на работу в выходной и все переделать, но боитесь коммитить свои изменения, так как не уверены на 100%, что ваши идеи лучше, чем у этого рехнувшегося дизайнера. Джим курит траву практически все время с момента пробуждения до момента отхода ко сну. Вы не хотите использовать это против него, да и все думают, что эта привычка никого не касается до тех пор, пока дизайны в порядке. Но всему есть предел. Так ведь? И дизайны у Джима не в порядке, и вообще он дерзкий какой-то.<br> <br> При работе с Mercurial вы можете просто создать клон всего репозитория:<br> <br> <img src="http://habrastorage.org/storage/68c027bf/7ef55f11/c341dc59/60dc90f0.png"><br> <br> Это не настолько расточительно, как может показаться. Так как в репозиториях <b>recipes</b> и <b>recipes-experiment</b> хранится одно и то же (пока), то Mercurial воспользуется "<a href="http://ru.wikipedia.org/wiki/%D0%96%D1%91%D1%81%D1%82%D0%BA%D0%B0%D1%8F_%D1%81%D1%81%D1%8B%D0%BB%D0%BA%D0%B0">жёсткими ссылками</a>" (hard links). А значит, копия репозитория будет создана быстро и не займет много дополнительного места на диске.<br> <br> Теперь можно сделать ряд изменений в экспериментальной ветке:<br> <br> <img src="http://habrastorage.org/storage/96ad9731/6fd2c79f/d458d7b9/235b60bd.png"><br> <br> Начинаем мой великий эксперимент над рецептом гуакамоле:<br> <br> <img src="http://habrastorage.org/storage/c49c10f0/cfdb23e3/4d84fb94/fa0ded5b.png"><br> <br> В экспериментальный репозиторий можно коммитить без опасений:<br> <br> <img src="http://habrastorage.org/storage/71deac19/a844b427/b4ed24c9/e60a80d9.png"><br> <br> Вы можете смело вносить изменения, фиксируя результат когда захотите. Это дает вам всю мощь контроля версий даже для вашего безумного эксперимента, причем никто не пострадает.<br> <br> Если вы решите, что эксперимент не удался, то можете просто удалить весь каталог с экспериментальным репозиторием. Нет репозитория — нет проблемы.<br> <br> Но если все получилось, то вам нужно лишь протолкнуть ваши новые правки:<br> <br> <img src="http://habrastorage.org/storage/01fcf609/6a0e9029/b4787faa/73f02234.png"><br> <br> И куда же они протолкнулись?<br> <br> <img src="http://habrastorage.org/storage/5b52ac76/64573441/dfe23550/342d9ba9.png"><br> <br> <blockquote>

hg paths

<br> отображает список известных удаленных (remote) репозиториев.<br> </blockquote><br> <br> Строчка, начинающаяся с «default», содержит путь к репозиторию, в который

hg push

проталкивает изменения если вы явно не укажете другой репозиторий. Обычно в этой строчке указан путь к репозиторию, с которого вы делали клон. В данном случае это локальный каталог, но в качестве пути может быть и URL. <br> <br> <img src="http://habrastorage.org/storage/f6f677ed/a911d2d6/f822cef7/33993dea.png"><br> <br> Не забывайте, что проталкивание изменений в этот <i>репозиторий…</i><br> <br> <img src="http://habrastorage.org/storage/5b3e3e5b/cf6dbd5e/0f29418a/c0738e7e.png"><br> <br> … не приводит к тому, что изменения появляются в рабочем каталоге.<br> <br> <img src="http://habrastorage.org/storage/742d905e/607cbf55/51688a01/bb5b1f96.png"><br> <br> <blockquote>

hg parent

<br> отображает набор изменений, находящийся в рабочем каталоге.<br> </blockquote><br> <br> Видите? Правки про «Queso» в пятом наборе изменений. Но в моем основном репозитории работа остановилась на четвертом наборе изменений. От того, что кто-то протолкнул изменения в <i>репозиторий</i>, рабочий каталог не обновился, и пятый набор изменений в нем не появился. Так что я по-прежнему работаю с четвертым набором изменений.<br> <br> <img src="http://habrastorage.org/storage/81287b1f/9096f4a3/eae68e64/5fe130a5.png"><br> <br> Если я захочу узнать, что в пятом наборе изменений, то мне нужно будет использовать команду

hg update

:<br> <br> <img src="http://habrastorage.org/storage/023fc2aa/41243289/e94f5f67/35276977.png"><br> <br> Видите, что произошло? Изменения были получены, но они были после той версии, с которой я работал. Команды

push

и

pull

просто пересылают изменения между репозиториями. Эти команды не влияют на то, с чем я работаю в данный момент.<br> <br> Сейчас репозитории выглядят так:<br> <br> <img src="http://habrastorage.org/storage/6ebe8da2/5fac7827/7dd53ab1/5a118ca1.png"><br> <br> Mercurial гибок в вопросах пересылки изменений из репозитория в репозиторий. Можно протолкнуть изменения прямо из экспериментального в центральный репозиторий:<br> <br> <img src="http://habrastorage.org/storage/5b5c8de5/3a4fa941/a7e099f2/bc357932.png"><br> <br> Так пятый набор изменений был отправлен из экспериментального прямиком в центральный репозиторий. Теперь, если я вернусь в свой основной репозиторий, то увижу, что в нем больше нечего проталкивать!<br> <br> <img src="http://habrastorage.org/storage/bbd0ef75/4601b945/c3774a27/4df5c17c.png"><br> <br> Это потому, что Mercurial знает, что в центральном репозитории этот (пятый) набор изменений уже откуда-то есть. Это по-настоящему полезно, потому как иначе Mercurial мог бы попытаться применить изменения заново и серьезно запутаться.<br> <br> Дизайнер Джим, после того как ему предложили работу, пообещал приступить к делам сразу же. Однако он не появлялся на работе еще два месяца. Почти все уже забыли и о нем, и о том, что предлагали ему работу, так что когда он весь такой загорелый впервые появился в офисе, честно сказать, никто толком не мог понять, кто он и что вообще происходит. Это было достаточно забавно. Внешность у него типическая. В конце концов, во всем разобрались, но так как он был новеньким, все постеснялись спросить у него, что, черт побери, произошло. И про шрамы и синяки на лице тоже не спросили. Неважно. Просто мы ненавидим этого парня.<br> <br> Иногда случается, что спустя месяцы, вы обнаруживаете, что сделали ошибку.<br> <br> <img src="http://habrastorage.org/storage/deaea912/fe92dd6c/ec887aaa/889f199f.png"><br> <br> Картофельные чипсы? Чё за..?!<br> <br> Mercurial может изъять старый набор изменений из истории. Mercurial смотрит на набор изменений, определяет обратные действия и изменяет текущий рабочий каталог. Давайте попробуем изъять ту старую ревизию номер 2.<br> <br> <img src="http://habrastorage.org/storage/4667451a/25bdb499/f632481c/2a066f45.png"><br> <br> Матерь божья, что это было?<br> <br> <img src="http://habrastorage.org/storage/fd39bd64/6a0afc42/b16be42c/96ff7f13.png"><br> <br> Вообще говоря, времени могло пройти много. Чипсы вообще могли исчезнуть из рецепта. Много всего жуткого могло произойти. А значит, иногда после изъятия ревизии объединить изменения невозможно. В таких случаях вы получите конфликты слияния (merge conflicts), которые вам нужно как-то разрешить. Вот об этом и поговорим в следующей части.<br> <br> <h5>Проверь себя</h5><br> <br> Вот то, что вы должны уметь делать после прочтения данной части:<br> <ol> <li>Откатить случайные изменения. До того, как они зафиксированы в репозитории, и после.</li> <li>Локально склонировать репозиторий для экспериментов.</li> <li>Проталкивать изменения в разные репозитории.</li> <li>Откатить старую ошибку, которая давным-давно была зафиксирована в репозитории.</li> </ol><br> </html>

Продолжение здесь: Часть 5. Процесс слияния