GitUM
GitUm (Git Upstream Manager) — средство для поддержки работы над ответвлением проекта в git-репозитории
Gitum имеет 5 рабочих веток:
1. Ветка rebased с патчами наверху — рабочая ветка, создаётся локально.
2. Ветка current с непрерывной историей изменений.
3. Ветка patches с патчами в виде отдельных файлов — каждый коммит это состояние репозитория.
4. Ветка upstream - копия апстрим-ветки.
4. Ветка gitum-config с конфигурационным файлом, где содержатся имена 4-х предыдущих веток. Носит всегда название gitum-config. Может отсутствовать - используются имена веток по умолчанию.
Создадим конфигурационный файл gitum
gitum create [ --remote REMOTE ] [ --upstream UPSTREAM ] [ --rebased REBASED ] [ --current MAINLINE ] [ --patches PATCHES ]
Где
- REMOTE — апстрим репозиторий/ветка (или просто любая локальная ветка — тогда без /), из которой будем тянуть изменения;
- UPSTREAM — наша копия ветки origin/master;
- REBASED — ветка с нашими патчами наверху;
- MAINLINE — отображает последовательную историю;
- PATCHES — ветка с нашими патчами в виде отдельных файлов.
Три последние локальные ветки создаются сами. Ветка upstream либо берётся существующая, либо к указанному названию приводится текущая активная ветка. Репозиторий апстрим или локальная ветка, из которой берутся изменения тоже должны существовать. (Указанные значения являются значениями по умолчанию в случае, в случае если create запускается без параметров.)
В случае запуска без переметров
gitum create
текущая ветка переименовывается в upstream и создаются ветки rebased, mainline и patches.
Перенесём изменения из апстрим репозитория
gitum merge [ --track ] [--branch BRANCH] [ --continue | -- abort | -- skip ]
В процессе merge могут возникать конфликты слияния. Нужно разрешить очередной конфликт, добавить исправленные файлы командой
git add
и продолжить процесс:
gitum merge --continue
Если же вы передумали делать merge, то можно вернуть изначальное состояние актуальных веток с помощью команды:
gitum merge --abort
Либо пропустить текущий патч и продолжить процесс:
gitum merge --skip
В результате в ветке разработки mainline у нас появятся копии коммитов из удалённой ветки (сохранено описание, авторство и, по возможности,функционал). Так же вы сможете заметить, что история остаётся непрерывной и отсутствие коммитов вида: "Merge remote into local". Так же можно указать вручную с какой веткой проводить слияние, указав вначале:
gitum merge --branch local_branch
или
gitum merge --branch remote1/branch1
Опция --track позволяет сохранить указанную ветку для использования по умолчанию.
Сохраним изменения в gitum репозиторий
После того, как мы изменили ветку rebased (добавили коммиты или изменили старые), надо обновить ветки mainline и patches:
gitum update [ --message MESSAGE ]
Возможны два сценария:
- В ветку rebased были добавлены новые коммиты поверх. Тогда команда автоматически перенесёт данные коммиты в gitum.
- В ветке rebased были произведены любые другие изменения, кроме случая описанного в (1): изменение коммитов, добавление в середину, удаление коммитов и прочее. Тогда команда добавит результирующий diff между ветками rebased и mainline в gitum и предложит ввести сообщение коммита, если не указан параметр --message.
Восстановим исходное состояние рабочей ветки
Если после модификации ветки rebased решено вернуть её в предыдущее состояние, то используется команда
gitum restore [ --commit COMMIT ] [ --full]
которая так же принимает опцию --commit из ветки patches (по умолчанию — HEAD из patches).
В случае потери всех веток используется опция --full.
Склонируем удалённый gitum репозиторий
gitum clone GITUM-REPO DIR
что склонирует репозиторий по адресу GITUM-REPO в директорию DIR.
Вытянем изменения из удалённого gitum репозитория
gitum pull [ --remote REMOTE ] [ --track ]
при этом наши локальные патчи расположатся поверх новых изменений — история сохраняется.
Если в процессе наложения возникли проблемы, то нужно их исправить, сделать git add и дать команду
gitum pull --resolved
или пропустить текущий патч (--skip), или прервать процесс и вернуть первоначальное состояние репозитория с помощью
gitum pull --abort.
Опция --track позволяет сохранить указанный удалённый репозиторий для использования по умолчанию.
Сохраним изменения в удалённый gitum репозиторий
gitum push [ --remote REMOTE ] [ --track ]
Опция --track позволяет сохранить указанный удалённый репозиторий для использования по умолчанию.
Удалим gitum файлы из репозитория
gitum remove [ --full | --branches | --configfiles ]
Дополнительно
- У gitum есть опция --repo ПУТЬ, которая указывает путь до gitum-репозитория. Если опция не указана, то поиск ведётся в текущем каталоге.
Примеры использования
Сюжет 1. Разработчик вносит изменения, создавая новые коммиты.
Разработчик вносит изменения в ветку rebased, делает коммит своих изменений, указывая для них описание.
Для полного внесения изменений в репозиторий достаточно выполнить команду gitum update, которая ничего не будет спрашивать, просто распределит нужным образом новые коммиты, создав необходимое число коммитов в mainline.
Сюжет 2. Мерж с апстримом
Изменения из апстрима вынимаются в виде отдельных коммитов, при этом выполняется git rebase, возможно, выполняющий (возможно, с ручным вмешательством) изменение созданных у нас коммитов.
В результате в mainline должны быть перенесены уложенные поверх наших патчей коммиты апстрима (с их собственным описанием), в rebase все наши патчи расположены поверх новых коммитов из апстрим, а в patches занесены новые версии наших патчей.
Замечания
- В рамках борьбы с абортами предлагаю заменить --abort на --abandon
Выполнено в 0.7.0-alt1:
- Должен быть скрипт для тестирования (создание репозитория, веток, выполнение основных команд, проверка появления необходимых файлов)
- Должен работать просто gitum create (с параметрами по умолчанию)
- При начальной инициализации требует, чтобы ветка upstream была заранее руками создана — зачем это нужно?
- Нужен пример создания gitum-репозитория на примере удалённого (с github)
- При gitum update предлагает ввести описание коммита для mainline (где наследование?!): При update из rebased должны переноситься новые коммиты по отдельности (без вопросов об описании коммита), плюс изменения в репозитории, если есть, с запросом коммита.
- В ветке patches полное дерево зачем-то ещё есть — можно от него избавится?
- Просто gitum pull не работает
- Релизовать поддержку работы не из корня
Исходный код
Ссылки
Почему не merge
- http://gitready.com/advanced/2009/02/11/pull-with-rebase.html
- http://randyfay.com/node/103 : git config --global branch.autosetuprebase always
- http://gitevangelism.blogspot.com/2011/02/git-push-force-and-merging-without.html
- http://libav.org/git-howto.html (Проект libav: «merge commits are forbidden»)
- http://www.kerrybuckley.org/2008/06/18/avoiding-merge-commits-in-git/
- http://yannesposito.com/Scratch/en/blog/2010-03-23-Encapsulate-git/
Обратная точка зрения:
Заключение
Просьба ко всем, кому интересен данный проект его попробовать и написать свой отзыв в багу: http://bugs.etersoft.ru/show_bug.cgi?id=7690.
Приветствуются любые замечания и пожелания с вашей стороны!