Подтвердить что ты не робот

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

Однако это не похоже на "правильный" способ справиться с этим. Любые предложения?

4b9b3361

Ответ 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 иначе, чем другие.)

На самом деле, я думаю, вы бы хотели ввести политику только изменения номера версии в вашей производственной ветки (той, из которой вы создаете релизы), или в ветвях, которые предназначены только для целей выпуска (например, изменение версии числа), и которые вы никогда не намерены сливаться с ветвью развития.

Я еще не использовал эту стратегию, но думал только об этом, и я думаю, что я начну попробовать.