Recently I needed to take part of a monolithic Subversion repository, and create a new, smaller repository, while keeping all of the
history intact. For all intents and purposes, I needed to move:
to its own repository rooted at
Oh, and to make matters more fun, I don’t have admin access to any of these repos.
The easy way to copy things from one repository to another is do an
svn export followed by an
svn import to the new
repository. This works, but you lose all of the history, which is a bummer.
Another possibility to keep all of the revisions intact is to use
git-svn to clone the subversion repository with history
and then use it as a basis to populate a new subversion repository. I haven’t tried it, but something like this would probably work:
git svn clone [args] [subversion repo] temp-repo
Follow the instructions here on Google Code but when you fetch, fetch from
temp-repo you just created.
One nice thing about this approach is that it requires nothing on the subversion server side to work. The downside is that you will
probably lose dates and user information in the history.
Sync + Filter
Probably the most robust way to do this is without physical access to the svn server is to create a local repository, mirror the source
repository, filter out everything that is NOT what you want to copy, and then sync that with the destination repo. There are a few steps
involved and it’s better to actually get access to both repositories (then you can just use Subversion’s admin tools) to get everything,
but in the absence of access to the servers, then svnsync is the next best
thing to get a repository’s contents, with history.
svnadmin create temp-repo
echo "exit 0" > pre-revprop-hook
chmod a+x pre-revprop-hook
svnsync initialize file://[path-to-temp-repo] https://svn.example.com/lots_of_projects
svnsync synchronize file://[path-to-temp-repo]
svnadmin dump ./temp-repo > everything.dump
cat everything-dump | svndumpfilter include project_a --drop-empty-revs --renumber-revs > project-a-dump
svnadmin create project_a; svnadmin load project_a < project_a_dump
svnsync initialize https://svn.example.com/project_a file://[path-to-project_a-repo]
svnsync synchronize https://svn.example.com/project_a
In essence, what we are doing is creating a local mirror copy of the big repo that we can play with. Once we have a mirror that we can
manipulate, we can dump its history and filter out only the project that we are interested in. Once we have that, we create a new local
repo with only those commits in it, and synchronize it with its new home.
The only problem with this approach is that there needs to be a pre-revprop-hook installed on the target repository, which will
require some cooperation from the administrator of that repository.
If anyone else knows of a way to copy part of a subversion repository with all of its history, I would love to hear it.