Git -svn: reset отслеживание для мастера
Я использую git-svn
для работы с репозиторием SVN. Мои рабочие копии были созданы с помощью git svn clone -s http://foo.bar/myproject
, чтобы моя рабочая копия соответствовала схеме каталога по умолчанию для SVN (соединительная линия, теги, ветки).
Недавно я работал над ветвью, которая была создана с помощью git-svn branch myremotebranch
и извлечена с помощью git checkout --track -b mybranch myremotebranch
. Мне нужно было работать из нескольких мест, поэтому из веток я git-svn dcommit
-ed файлов в репозиторий SVN достаточно регулярно.
После завершения моих изменений я переключился на мастер и выполнил слияние, совершил слияние и попытался выполнить успешное слияние с удаленной стволом.
Кажется, что после слияния удаленное отслеживание для мастера переключилось на ветку, над которой я работал:
# git checkout master
# git merge mybranch
... (successful)
# git add .
# git commit -m '...'
# git svn dcommit
Committing to http://foo.bar/myproject/branches/myremotebranch ...
#
Есть ли способ обновить мастер так, чтобы он следовал за remotes/trunk
, как и до слияния?
Я использую git 1.7.0.5, если это поможет.
Было бы полезно, если бы вы также могли объяснить, почему это произошло, поэтому я могу избежать повторения проблемы. Спасибо!
Edit:
Вот мой текущий .git/config
:
[core]
repositoryformatversion = 0
filemode = true
bare = false
logallrefupdates = true
autocrlf = false
[svn-remote "svn"]
url = http://foo.bar/myproject
fetch = trunk:refs/remotes/trunk
branches = branches/*:refs/remotes/*
tags = tags/*:refs/remotes/tags/*
[branch "mybranch"]
remote = .
merge = refs/remotes/myremotebranch
Итак, кажется, что ствол указывает на правильное место. Однако переход на ветку, а затем обратно к мастеру не помогает; git svn dcommit
в мастер все еще пытается нажать на myremotebranch
.
Ответы
Ответ 1
Если в trunk нет изменений, git выполняет быстрое переключение и просто устанавливает локальную ветвь "master" на фиксацию в вашей ветке. Git -svn не знает, как совершать быстрые переходы слияния обратно в магистраль, на самом деле он думает, что "мастер" теперь указывает на ветвь svn.
Чтобы обойти это, используйте git merge --no-ff
при слиянии. Это заставит git создать фиксацию слияния, которая затем может быть передана в svn.
Ответ 2
Если вы git svn rebase
после переключения на мастер и используете --squash, вы можете избежать этого.
# git checkout master
# git svn rebase //(<--the missing step)
# git merge --squash mybranch // (<-- doesn't commit, more like an svn merge would do)
... (successful)
# git add .
# git commit -m '...'
# git svn dcommit
Committing to http://foo.bar/myproject/trunk...
#
Чтобы решить текущее состояние (т.е. ваш мастер указывает на ветвь SVN)
Вы можете "переключиться" на другую ветвь, удалить мастер, "переключиться" на нее, а затем снова слить:
# git checkout mybranch
# git branch -D master
# git checkout -b master trunk
... continue with merge...
# git merge --squash mybranch
... теперь у меня mybranch сливается в master и готов к commit
, а затем dcommit
до trunk
Ответ 3
Если вы не сделали фиксацию на главном, это означает, что git merge mybranch
был быстрым: master HEAD
просто перейдите к mybranch HEAD
.
Это может объяснить, почему git svn dcommit
нажал ваши изменения на SVN mybranch
.
Это было бы:
- сначала обновить соответствующую ветвь SVN с последним Git
mybranch
, который еще не завершен,
- запись слияния в магистраль со стороны SVN
- а затем он будет переустанавливать мастер на стороне Git (ничего не делать, уже там).
Я не думаю, что мастер не изменил свою ссылку, но если у вас есть сомнения (и ваш рабочий каталог чист), вы можете (если мастер в настоящий момент проверен):
git reset --hard remotes/trunk
Ответ 4
В общем, вы не должны использовать git merge
с git svn
, потому что svn, даже с ветвями, не поддерживает вид отслеживания слияния, который делает git. Когда вам нужно объединить ветку, я имел наибольший успех (по крайней мере, с недавним svn), выполняющим простой процесс проверки/слияния svn, а затем используя git svn rebase
для обновления моих хранилищ git -svn. Это сохраняет svn собственные метаданные отслеживания слияния, которые (AFAIK) git-svn
полностью не знают.
Я не совсем уверен, в каком состоянии находится ваш репозиторий svn. Я бы проверял, чтобы слияние dcommit делало то, что вы хотели, чтобы оно было на багажнике. Даже если бы это произошло,
Бьюсь об заклад, если вы посмотрите на содержимое файлов refs/heads/master
и refs/remotes/trunk
в своем репо, вы увидите, что они разные на данный момент. Если это так, я бы (без каких-либо локальных изменений) сделал git-svn fetch
, а затем git branch -f master remotes/trunk; git reset --hard master
для повторной синхронизации ветки git с веткой отслеживания git -svn. Если у вас есть локальные изменения, вам придется совершить и сделать что-то вроде git rebase master^4 --onto remotes/trunk
, где 4 - количество коммитов, которые необходимо сохранить. В качестве альтернативы, если все они не зарегистрированы, сначала запустите их git stash
.
В противном случае вы всегда можете получить все в svn и просто стереть репо и получить новую проверку.
Ответ 5
Мы успешно использовали git merge --squash
в развитии ветки git -svn. Проблема с git -svn заключается в том, что, хотя ваш локальный git -svn-клон может хранить информацию о слиянии, как только вы dcommit в репозиторий svn, он потерян.
Таким образом, для других пользователей (git -) svn комманды слияния выглядят так же, как и обычные коммиты. Сквош хорош для того же самого, что и git merge --no-ff
(например, создание фиксации слияния на master), но также включает список фактических коммитов, сделанных в объединенной ветке, которые в противном случае были бы потеряны при dcommitting.
Ответ 6
У меня была такая же проблема, и я объединил удаленные/удаленные соединительные линии в мастер, после чего git svn информация указала обратно на trunk
У меня не было времени, чтобы активировать dcommit, когда я покидал проект, и мой репозиторий git -svn умер с моим хулигасом. Я попробовал dcommit -dry-run, и он сказал, что он вернется в багажник.
Я воспроизведу настройку и тест, когда получаю время
веселит