2

I am trying to convert a slightly messy svn repository to git. I tried reading some guides and other SO questions, but get a little lost as to what's the best way to follow.

The SVN repository has a top-level folder structure with folders, something like:

 |- client
 |- server
 |- website
 |- misc

Most of those folders have the 'standard' svn structure: i.e. trunk, branches and tags. Some are just flat folders however.

 |- client
    |- trunk
    |- branches
    |- tags
 |- server
    |- trunk
    |- branches
    |- tags
 |- website
 |- misc

The branches and tags might have the same name between different folders. For example, both client and server folders might have a branch called 1.0.

I managed to convert individual folders using svn2git, and it seems to get the history, as well as branches fine. I can manage to create an individual git repository for each folder. However, I'd like to keep everything in one repository eventually.

What's the best way to merge those folders (now git repositories) into one, whilst maintaining the branches, tags and history of each folder? Using this approach, I seem to lose both the commit history and the branches from the merged-from repository... Or perhaps I'm just missing some important steps or doing something wrong?

Otherwise, maybe using svn2git on each folder separately is not the best approach to migrate from svn to git?

Community
  • 1
  • 1
gingerlime
  • 5,206
  • 4
  • 37
  • 66

2 Answers2

1

I eventually opted for the approach on this answer.

Essentially:

  • creating a git project for each sub-folder in the svn repository (using svn2git)
  • creating a new git repository merging all repositories into
  • adding each project (including all branches) as a remote:

    git remote add alpha <url/path-to-alpha-repo>
    git remote add bravo <url/path-to-bravo-repo>
    git remote add charlie <url/path-to-charlie-repo>
    for r in $(git remote); do
      git config remote.$r.fetch \
      "$(git config remote.$r.fetch | sed -e 's.remotes.heads/all.')"
      git config --add remote.$r.fetch \
      "$(git config remote.$r.fetch | sed -e 's.heads.tags.g')"
      git config remote.$r.tagopt --no-tags
    done
    git remote update
    
  • pushing the merged-repository to a remote repository (from now on this will be the 'official' repository).

Community
  • 1
  • 1
gingerlime
  • 5,206
  • 4
  • 37
  • 66
0

I would rewrite the svn repository to the following structure before converting to Git:

- trunk
  |-client
  |-server
  |-website
  `-misc
- branches
  |-client
  |-server
  |-website
  `-misc
- tags
  |-client
  |-server
  |-website
  `-misc

To restructure your svn repository, you'll have to svnadmin dump the repository to a file, update all paths in that file, and then svnadmin load the updated dump file into a new repository.

Have a look at the structure of the dump file - the actual restructuring can be easily done with an editor that supports search/replace. It needs to be binary-safe though since besides the ascii metadata the dump file also contains raw binary data (of binary files in the repository).

ThiefMaster
  • 310,957
  • 84
  • 592
  • 636
  • Thanks. Sounds like an interesting approach, but are you aware of any resources/tools to help do this safely? I had a quick look on an svn dump I have and wouldn't really know where to start (let alone deal with issues of merging e.g. two branches with the same name for client and server...) – gingerlime May 05 '12 at 11:22
  • 1
    http://svn.apache.org/repos/asf/subversion/trunk/notes/dump-load-format.txt - search for `Node-path` in the dump file. If you performed copy/move operations, `Node-copyfrom-path` might be relevant, too. – ThiefMaster May 05 '12 at 11:26
  • This stuff seems way over my head to be perfectly honest... Doing some regex search/replace on such a massive scale messing around with the svn internal dump format isn't exactly the solution I was hoping for. Thanks for suggesting this direction though! – gingerlime May 05 '12 at 12:29