My colleague and I are having an vigorous discussion about merge strategies and I'm hoping we can get some information to help resolve it.
The tl:dr is: Should we use merge or rebase when pulling changes from a remote branch so that we are not constantly redoing the conflict resolution.
- svn: our master golden repository
- trunk: git remote branch tracking svn. Used to stage the git change before dcommitting to subversion.
- feature-branch: git remote branch where the work of 2+ colleagues on one feature is combined
- colleague1: First colleague's local branch
- colleague2: Second colleague's local branch.
We are using the Sebastien Varette's excellent workflow from Is git-svn dcommit after merging in git dangerous?.
The problem we are getting is that every time colleague1 rebases from svn (by rebasing to trunk and then rebasing to colleague1 before pushing to feature-branch when done) then commits on feature-branch which conflict against each other have to be re-done. The same conflict resolution has to be done time and time again - every time the svn rebase workflow is done.
Note that we are using git rebase mirror un-3451
for this rebase.
My argument is that we should use git merge mirror un-3451
. My understanding is that this would yield a commit which is marked as the merge of two previous commits. Therefore, git would know not to use the previous commits but using the merge commit instead.
My colleague, on the other hand, argues that using merge will make the eventual merge with svn much harder and much prefers using rebase. He finds it easy - sadly he's not the one resolving all the conflicts. He argues that using a squash commit would yield the same effect.
My argument is that the merge has the same effect as a squash but includes marking the commits that were included.
State 1
svn-trunk: A
\
git-trunk: A'
\
remote-feature: A'-----C
\ /
c1-feature: A'--C
\
c2-feature: A'--D
State 2
C conflicts with D on File 1(F1). F1 has the conflict resolved so D becomes D'.
git pull --rebase remote feature
git add F1
git rebase --continue
git push
Commit graph:
svn-trunk: A-----B
\ \(svn rebase)
git-trunk: A'----B'
\
remote-feature: A'-----C---------D'
\ / \ /
c1-feature: A'--C \ / (git push)
\ \ /
c2-feature: A'-------C--D'
State 3
Now, colleague1 wants to pull in the changes from svn-trunk:
git checkout trunk
git svn rebase
and then rebase them onto c2-feature
git checkout feature-branch
git rebase trunk
The rebase puts B1 onto c2-feature and then C and then grabs D' and forces the same conflict resolution to become D''
Commit graph:
svn-trunk: A--------B
\ \(svn rebase)
git-trunk: A'--------B'
\ \
remote-feature: A'-----C--\-----D'
\ / \--\--\ \
c1-feature: A'--C \ \ \
\ \ \ \
c2-feature: A'----------B'-C--D''
Each time the git checkout trunk; git svn rebase; git checkout feature-branch; git rebase trunk; git push remote
cycle happens all the conflict resolutions have to be done again and again.
Questions
- if you rebase from svn, push to the remote branch, have colleague2 push some commits to the remote branch and, then later on, colleague1 does a pull merge from remote branch will the resulting merge commit mention the svn commits (and therefore cause a problem on subsequent rebases).
- Which is better in the scenario above: rebase or merge?
- Would the rerere functionality be of more use?
Many thanks!