How do I tell git-svn about a remote branch created after I fetched the repo?

Viewed 76830

I'm using git-svn to work against my company's central Subversion repository. We've recently created a new feature branch in the central repo.

How do I tell Git about it? When I run git branch -r I can only see the branches that existed when I ran fetch against the Subversion repo to initialize my Git repo?

9 Answers

If you want to track ALL the remote svn branches, then the solution is as simple as:

git svn fetch

This will fetch ALL the remote branches that have not been fetched yet.

Extra tip: if you checked out only the trunk at first, and later you want to track ALL branches, then edit .git/config to look like this and re-run git svn fetch:

[svn-remote "svn"]
        url = https://svn/path_to_repo_root/
        fetch = path_to_trunk:refs/remotes/git-svn
        branches = path_to_branches/*:refs/remotes/*

The key points are url should point to the repository root, and the paths defined in fetch and branches should be relative to url.

If you want to fetch only specific branches instead of ALL, there is a nice example in git svn --help:

[svn-remote "huge-project"]
        url = http://server.org/svn
        fetch = trunk/src:refs/remotes/trunk
        branches = branches/{red,green}/src:refs/remotes/branches/*
        tags = tags/{1.0,2.0}/src:refs/remotes/tags/*

With older versions of git-svn, once you specified branches like this, you might not be able to get new branches with git svn fetch. One workaround is adding more fetch lines, like this:

[svn-remote "huge-project"]
        url = http://server.org/svn
        fetch = trunk/src:refs/remotes/trunk
        fetch = branches/blue:refs/remotes/branches/blue
        fetch = branches/yellow:refs/remotes/branches/yellow
        branches = branches/{red,green}/src:refs/remotes/branches/*

Another workaround by @AndyEstes: edit .git/svn/.metadata and change the value of branches-maxRev or tags-maxRev to a revision before any newly-specified branches or tags were created. Once you've done this, run git svn fetch to track the new svn remote branch.

It appears I just needed to git svn fetch; somehow I had convinced myself that would fetch the entire repo instead of just the changes.

Maybe I messed it up somehow but I followed the instructions in vjangus' answer and it almost worked. The only problem was that newbranch didn't appear to be branched from the trunk. In gitk, it was kind of "floating" all on its own; it had no common ancestor with the trunk.

The solution to this was:

  1. Find the SHA1 of the last commit that happened on trunk before the branch was created.
  2. Find the SHA1 of the first commit on the new branch (message is probably "Created new branch, copied from trunk@12345" or something)
  3. git diff-tree <sha1 from step 1> <sha1 from step 2> -- there should be no output. If there is output, you may have selected the wrong commits.
  4. git checkout local-newbranch then git rebase <sha1 from step 1>. This will rebase local-newbranch onto the new tree but remotes/newbranch will still be disconnected.
  5. Go to the file .git/refs/remotes/newbranch and edit it to contain the full SHA1 of the new commit (on the rebased newbranch) that corresponds to the old commit it's currently pointing at. (Or maybe use git-update-ref refs/remotes/newbranch <new-SHA>. Thank you inger.)
  6. The next time you git svn dcommit to newbranch, you'll get a bunch of messages about it updating some log. This is normal I think.

I recommend keeping gitk --all open the whole time and refreshing it often to keep track of what you're doing. I'm still sort of new to git and git svn so please suggest improvements to this method.

Related