Last active
August 29, 2015 13:56
-
-
Save jrsmith3/9250710 to your computer and use it in GitHub Desktop.
Split a monolithic git repo into several small ones
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# -*- coding: utf-8 -*- | |
""" | |
I used the following script to convert each subdirectory of work.git into its own git repo. The one exception was paper-2013.01.16_nea_collector which I did by hand using essentially the same method as below, except I skipped the part where I removed the tags. I used the procedure found at [1] and slightly modified it. I also used the solution in [2] to convert non-bare repos to bare. Note also that I first cloned work from its bare git repo on the SD card, removed the remote, and tarred the result to work.tar. | |
[1] http://stackoverflow.com/questions/359424/detach-subdirectory-into-separate-git-repository | |
[2] http://stackoverflow.com/questions/1784506/when-creating-a-git-repository-that-will-be-on-the-server-can-i-convert-it-to-a | |
""" | |
import os | |
import subprocess | |
import shutil | |
subprocess.call(["tar","xf","work.tar"]) | |
contents = os.listdir("work") | |
for dirname in contents: | |
if dirname[0] is not ".": | |
os.chdir("work") | |
# Remove the tags. | |
print("=" * 50) | |
print "="*5, dirname, "="*5 | |
print("removing tags") | |
git_tag = subprocess.Popen(["git","tag","-l"],stdout=subprocess.PIPE) | |
git_tag.wait() | |
xargs = subprocess.Popen(["xargs","git","tag","-d"],stdin=git_tag.stdout) | |
xargs.wait() | |
print("git filter-branch") | |
subprocess.call(["git","filter-branch","--tag-name-filter","cat","--prune-empty","--subdirectory-filter",dirname,"--","--all"]) | |
print("deleting the backup reflogs") | |
subprocess.call(["git","reset","--hard"]) | |
git_foreach = subprocess.Popen(["git","for-each-ref",'--format="%(refname)"',"refs/original/"], stdout=subprocess.PIPE) | |
xargs = subprocess.Popen(["xargs","-n","1","git","update-ref","-d"], stdin = git_foreach.stdout) | |
subprocess.call(["git","reflog","expire","--expire=now","--all"]) | |
subprocess.call(["git","gc","--aggressive","--prune=now"]) | |
print("Moving newly filter-branched repo to its own folder") | |
os.chdir("..") | |
shutil.move("work","split_repos/"+dirname) | |
print("Turning repo to bare, then removing the non-bare copy.") | |
os.chdir("split_repos") | |
subprocess.call(["git", "clone", "--bare", "-l", dirname, dirname + ".git"]) | |
shutil.rmtree(dirname) | |
os.chdir("..") | |
print("Un-taring the work git repo again.") | |
subprocess.call(["tar","xf","work.tar"]) | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment