Home > General > git-svn gotcha

git-svn gotcha

September 29th, 2008

I was having problems with the following setup the other day:

 [remote deveoper] <===>; [shared git repo] <===> [me] <===> [client's svn repo]

So my remote developer and I push and pull to/from the shared git
repo, and then I sync changes to and from the client’s svn repo using
git-svn.

Problem

My problem is, when I am ready to merge changes from my local master
branch to trunk-local, if I do a “git merge master” and then try to
issue any git-svn commands I get the following errors:

======================
$ git merge master
Updating d88106e..77b86ae
Fast forward
 community/pom.xml |    2 +-
 1 files changed, 1 insertions(+), 1 deletions(-)

$ git svn dcommit
Can't call method "full_url" on an undefined value at
/usr/local/git/libexec/git-core/git-svn line 425.

$ git svn rebase
Unable to determine upstream SVN information from working tree history
======================

The only way I’ve seem to be able to remedy this is if I add the
“subtree” merge strategy to the merge command:

git merge -s subtree master

Then git-svn doesn’t get confused about it’s repo, but when you look
at the repo using gitk, you see something like:

[trunk-local]--[remotes/trunk]  Merge branch 'master' into trunk-local
|
|
|    [master]--[remotes/origin/master]  "last master commit msg"
|    |
|    |
|  /
/

When I use the normal merge strategy then gitk shows all branches at
the same level, but git-svn is of course b0rked.

Solution

I tried asking a few people on #git (freenode irc channel for git) for help, but the problem was a bit too involved to explain on irc and have someon follow along, so instead what I did was I asked on the official git mailing list (git@vger.kernel.org) and I got an answer almost immediately from Björn Steinbrink with a solution that seems to work just great! His input was to use --no-ff when merging my changes into the svn tracking branch (trunk-local). Here is his explanation:

The original merge you did ended up as a fast-forward, ie. no merge
commit was created. I guess that your history is so, that somehow the
remotes/trunk stuff is reachable through the second parent of some merge
commit that exists in your history. But git-svn uses –first-parent to
find its upstream, so it cannot find that in your scenario. I guess it’s
best if you use “*git merge –no-ff master*” to force the creation of a
merge commit. Subtree happens to work because it implies –no-ff, but
I’m not sure whether there might be downsides to using the subtree
strategy, so I’d rather go with the explicit –no-ff and the normal
merge strategies.

Hopes this helps other’s in the same situation as I was in. Thanks Björn Steinbrink

Share and Enjoy:
  • Digg
  • del.icio.us
  • Facebook
  • Google Bookmarks
  • DZone
  • Reddit
  • TwitThis

About the Author

Craig Tataryn started his career as a Visual Basic programmer, but don't hold that against him! The system he helped create was a cutting edge, n-tiered revenue collection system whose transactions per second metric was off the charts! Around the year 2000 he discovered Struts and never looked back. A professional Java developer for close to a decade, Craig has worked on a wide variety of projects ranging from Recruiting, Purchase order, Revenue collection and Mortgage systems. More recently Craig has written web services for children's educational toys and has honed his skills on Wicket, Facebook and iPhone application development. "I love to learn and more importantly I love to teach. Hoarding knowledge is one of the most petty and selfish things you can do, especially as a contractor. This is why I always make it a point to document and share my knowledge with my client's employees"

craig General

  1. No comments yet.
  1. No trackbacks yet.