| コメント(0) | トラックバック(0)

最終更新日: 2009 年 6 月 11 日

CVSSubversion は開発現場で広く使われている ソフトウェア構成管理システム (または バージョン管理システム) です。筆者もこれまで CVSSubversion には大変お世話になっており、Piece Framework のソースコードも SourceForge.netSubversion サービスを使わせていただいております。

しかし、SourceForge.net のサービスは速度面で快適とは言い難く、以前から他のサービスへの移行を検討していました。現在は GitHub に移行することを決定し、少しずつ移行作業を進めている最中です。この記事では、Piece Framework のプロダクトのひとつ Stagehand_TestRunner を例として、Subversion から git への移行について実際に行った作業を記録しておきたいと思います。

ノート: SourceForge.net から GitHub への移行は無事完了しています。piece's Profile - GitHub (2009/6/11)
KUBO Atsuhiro

ゴール

今回のゴールは Stagehand_TestRunnerSubversion リポジトリを git の共用リポジトリに移行することです。まず、移行元のリポジトリレイアウトを示します。

+--branches
|  |
|  +--branch-1.0
|
+--releases
|  |
|  +--release-0.3.0
|  |  ...
|  +--release-2.6.2
|
+--tags
|
+--trunk

上記の要素のうち branches 以下のディレクトリと trunk を gitブランチ に、releases 以下のディレクトリを gitタグ にマッピングします。tags は空なので無視することにします。まとめると下記のようになります。

Subversionリポジトリgitリポジトリ
branchesブランチ
releasesタグ
tags-
trunkブランチ(master)

git-svn

git-svnSubversiongit の相互運用を可能にするコマンドです。git-svn コマンドにより Subversion リポジトリの一部または全体を git リポジトリに変換することができます。

git-svn コマンドは tags として指定された Subversion ディレクトリを git のブランチにマッピングします。例えば、上記の releases/releases-2.6.2tags/releases-2.6.2 にマッピングされます。今回は releases をタグとして扱いたいため、git-svn コマンドだけでは目的を達成できません。(実行後にいくつか作業を行う必要があります。)

svn2git

svn2gitgit-svn のラッパーですが、git-svn とは異なり、タグとして指定した Subversion ディレクトリを git のタグにマッピングします。svn2git には 2 つ 多くのバージョン があり、今回使わせていただいたのは Kevin Menard 氏による forkされたバージョン です。(オリジナルバージョン は筆者の環境では動作しませんでした。)

ノート: Kevin Menard 氏によるバージョンは下記のコマンドでインストールすることができます。
gem sources -a http://gems.github.com
gem install nirvdrum-svn2git
(2009/6/11)

これで思い通りのマッピングができると期待しましたが、そのままではモジュールのロードに失敗したり、tags/release-xxx がタグに変換されなかったりしたため、ソースコードにいくつか手を加えました。変更点は下記のとおりです。(このパッチを適用したバージョンは こちら からダウンロードすることができます。)

ノート: Kevin Menard 氏によるバージョン 1.3.1 ではこのような問題は発生しませんでした。よって下記のパッチを適用する必要はありません。(2009/6/11)
diff --git a/bin/svn2git b/bin/svn2git
index 2d2055c..aff089c 100644
--- a/bin/svn2git
+++ b/bin/svn2git
@@ -20,6 +20,9 @@
 # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 # THE SOFTWARE.
 
+require 'rubygems'
+gem 'svn2git'
+
 require 'svn2git'
 
 url = ARGV.shift
diff --git a/lib/svn2git/migration.rb b/lib/svn2git/migration.rb
index 06c2151..ca1deec 100644
--- a/lib/svn2git/migration.rb
+++ b/lib/svn2git/migration.rb
@@ -61,12 +61,12 @@ module Svn2Git
     
     def get_branches
       @remote = `git branch -r`.split(/\n/)
-      @tags = @remote.find_all { |b| b.strip =~ %r{^#{@options[:tags]}\/} }
+      @tags = @remote.find_all { |b| b.strip =~ %r{^tags\/} }
     end
     
     def fix_tags
       @tags.each do |tag|
-        id = tag.strip.gsub(%r{^#{@options[:tags]}\/}, '')
+        id = tag.strip.gsub(%r{^tags\/}, '')
         subject = `git log -1 --pretty=format:"%s" #{tag.strip()}`
         date = `git log -1 --pretty=format:"%ci" #{tag.strip()}`
         `export GIT_COMMITER_DATE="#{date}"`

svn2git を実行する

マッピングルールに基づいて svn2git のコマンドラインを構築し実行します。--authors オプションで示すリストに含まれていない author が現れるとコマンドは終了しますが、慌てずに author をリストに加えて再度コマンドを実行します。この場合、作業は途中から再開されるため作業用ディレクトリを削除する必要はありません。

mkdir stagehand-testrunner
cd stagehand-testrunner
svn2git \
    https://sh-testrunner.svn.sourceforge.net/svnroot/sh-testrunner \
    --verbose \
    --trunk trunk \
    --branches branches \
    --tags releases \
    --authors /path/to/authors.txt 2>&1 | tee svn2git.log

ローカルリポジトリの状態を確認する

マッピングルールに基づいた変換が正常に行われたか、git branchgit tag で確認します。

$ git branch
  1.0
  branch-1.0
* master
$ git tag
release-0.3.0
...
release-2.6.2

不要なブランチやタグがあればこの段階で削除しておくといいでしょう。もちろん、共用リポジトリへの反映後に削除することもできます。

$ git branch -D 1.0
Deleted branch 1.0.
$ git branch
  branch-1.0
* master

ローカルリポジトリの内容を共用リポジトリへ反映する

準備が整ったらローカルリポジトリの内容を共用リポジトリへ反映します。

git remote add origin git@github.com:piece/stagehand-testrunner.git
git push --all
git push --tags

Git の利用を開始する

移行に使った作業用ディレクトリを削除し、改めて git clone を実行します。

$ cd ..
$ rm -rf stagehand-testrunner
$ git clone git@github.com:piece/stagehand-testrunner.git
$ cd stagehand-testrunner
$ git branch -a
* master
  origin/HEAD
  origin/branch-1.0
  origin/master
$ git tag
release-0.3.0
...
release-2.6.2

これで移行は完了です。

使用したソフトウェアのバージョン

$ git svn --version
git-svn version 1.6.0.4 (svn 1.5.4)
$ gem list

*** LOCAL GEMS ***

nirvdrum-svn2git (1.3.1)

参考文献

更新履歴

  • 2009/6/11: 最新の svn2git に合わせて内容を見直した。
  • 2009/2/14: 公開
トラックバック(0)
  • このブログ記事のトラックバックURL:
コメント