Git слияние исправлений с несколькими ветвями
Я пытаюсь обернуть голову вокруг ветвящихся моделей git. Я смотрел на http://nvie.com/posts/a-successful-git-branching-model/ для некоторых идей и, исходя из Subversion, я действительно с нетерпением ждал перемен в одном место и объединить его со всеми ветвями, которые в нем нуждались. В Subversion мы закончили работу с большой копией кода.
Однако я до сих пор не понимаю этого полностью. Вот стандартный тип рабочего процесса, который у меня есть, и он всегда будет иметь конфликты.
# create new version branch
git checkout master
git checkout -b v3
vim pom.xml # change branch version to "3.1-SNAPSHOT"
git commit -a
git checkout master
vim pom.xml # change master version to "4.0-SNAPSHOT"
git commit -a
Итак, мастер находится в 4.0-SNAPSHOT, а ветвь - 3.1-SNAPSHOT.
Не хочу создать исправление на ветке и переместить его в тулбар.
git checkout v3
git checkout -b hotfix
vim file.txt # make a bugfix change
git commit -a
git checkout v3
git merge hotfix # this works fine
git checkout master
git merge hotfix # this has a conflict since both branches have changed the version
Я понимаю, почему это происходит, и это имеет смысл. Есть ли лучший способ сделать это?
Я прочитал про вишневый кит, который я тестировал и работает:
git checkout v3
git cherry-pick a518b0b75eaf28868
git checkout master
git cherry-pick a518b0b75eaf28868
Однако это не похоже на "правильный" способ справиться с этим. Любые предложения?
Ответы
Ответ 1
Действительно, ваш ответ зависит от того, хотите ли вы, чтобы ваши деревья были основаны на одной истории... Например, 4.0 основывается на последних 3.X + всех изменениях в 4.0...
Лично я не рекомендую его, как только вы решите начать новую ветку (-и) для новой версии. В определенный момент времени программное обеспечение принимает другое направление, поэтому ваши ветки также должны быть.
Это оставляет git cherry-pick
идеальным решением. Внесите изменения в любую ветку, имеющую наибольший смысл, а затем вишню выберите ее в более старые версии. Это то же самое, как если бы вы проверили прежнюю ветку и вручную применили одно и то же изменение и сделали новую фиксацию. Он держит его в чистоте и до предела.
Git merge или rebase собираются попытаться объединить историю ветвей вместе, каждый по-своему, что я подозреваю, что вы не хотите, когда исправления ошибок в backporting и т.д.
Ответ 2
Если вы хотите получить супер-техническую информацию об этом, вы можете создать исправление от общего предка:
git merge-base v3 master
git checkout -b hotfix <whatever you got from merge-base>
# make your fix
git checkout v3 && git merge --no-ff hotfix
git checkout master && git merge --no-ff hotfix
v3--------v3 (hotfixed)
/ /
ancestor----hotfix
\ \
master----master (hotfixed)
--no-ff
флаг есть, чтобы подчеркнуть, что Git создаст слияние фиксации, сохраняя hotfix
ярлыка ветки на кончике исправления, вместо того, чтобы тянуть ярлык к v3
или master
. (Вы можете опустить флаг и получить то же самое поведение, так как ветвь hotfix
имеет один коммит, которого нет в master
или v3
. Больше информации в документации.)
Лично я считаю, что это перебор. Я бы пошел с gahooa: сделайте исправление на ветке, которое имеет смысл, затем объедините или выберите вишню в зависимости от того, как вы хотите, чтобы ветки относились друг к другу.
Ответ 3
В случае, если вы работаете над веткой "4.0" и должны исправить "3.1", вы можете перебазировать "4.0" после принятия "3.1":
Убедитесь, что вы находитесь в ветке Feature 4.0:
git checkout 4.0
Сохраните текущую работу, чтобы вы могли проверить другую ветку:
git stash
git checkout 3.1
Делаем редактирование и фиксируем:
git commit -a -m "bug fix"
git checkout 4.0
Верните свои изменения:
git stash apply
Измените 4.0, чтобы он соответствовал текущей главе "3.1":
git rebase "3.1"
Ответ 4
Я тоже борюсь с этим вопросом, и я думаю, что если вы захотите немного изменить свою стратегию управления версиями (т.е. отходите от версий -SNAPSHOT, которые поощряет Maven), это можно решить, используя фиксированная версия (например, SNAPSHOT или 0.0.0-SNAPSHOT) для мастера (или независимо от вашей ветки разработки). (Суффикс SNAPSHOT важен, если вы используете Maven, поскольку Maven обрабатывает артефакты с версией SNAPSHOT иначе, чем другие.)
На самом деле, я думаю, вы бы хотели ввести политику только изменения номера версии в вашей производственной ветки (той, из которой вы создаете релизы), или в ветвях, которые предназначены только для целей выпуска (например, изменение версии числа), и которые вы никогда не намерены сливаться с ветвью развития.
Я еще не использовал эту стратегию, но думал только об этом, и я думаю, что я начну попробовать.