🐱

段階的にsvnからgitへ移行する

2023/05/28に公開

はじめに

svnからgitに移行したい。
でも諸事情で急にgitに切り替えるのは難しい。

そんなプロジェクトでsvnからgitに移行した備忘録です。

  • 老害svn大好きおじさんの反対
  • git使えない人達の教育
  • ビルド環境(Jenkins)の移行

そんなこんなで今日からgitです!!と切り替えることができず
段階的にgitへの移行しました。

第一段階の移行作業

まずはgitのリポジトリを作成しましょう。

mkdir svn-to-git
cd svn-to-git
git svn init --prefix=svn/ https://example.com/svn/hoge --trunk /trunk/repo
git fetch

prefixのsvn/はoriginの代わりになるものです。
おまじないなのでとりあえずつけましょう。

今回はtrunkのみを移行しましたがブランチも移行する場合は--branchesで指定すればokです。

全ての履歴を取得するためgit svn fetchはrev数にもよりますが、遅いです。
数時間ほどかかりますが一度きりなので気長に待ちましょう。

しくじってfetchし直すのもだるいので出来たらリモートにpushしちゃいましょう。

git remote add git@hostname:repo
git push origin master

次にgitでの開発の中心となるブランチを作成します。
私はdevelopにしましたが、お好みの名前にしてください。

開発フローについて

今回deveopを主軸にしたのはしばらくsvnと並行して開発するためです。
svnと同期するときに直線履歴でないと面倒くさいのでmaster==trunkとすることでわかりやすくなります。

まずはgitで開発してsvnにコミットする例です。

この場合はmasterにマージしてsvnにdcommitするだけです。

git checkout master
git merge --no-ff develop -m "close topic-A"
git svn dcommit -n
git svn dcommit

単純ですね。
masterにマージしてsvnにもコミットしただけです。
--no-ffをつけているのはgitの1コミット==svnの1コミットになるためです。
dcommitはgitのcommitではなくpushです。
dcommitのたびにsvnにコミットが作成されるわけじゃないので気をつけてください。
dcommitする前にはgit svn dcommit -nでsvnでコミットされる反映を確認するほうが精神衛生上良いかと思います。

ではこんな場合はどうしましょうか?

gitに取り込まれていない変更がある場合はsvnにコミットする前に取り込む必要があります。

git checkout master
git svn rebase
git merge --no-ff develop -m "close topic-B"
git svn dcommit

git svn rebaseを実行することでmasterにtrunkの変更を反映できます。
反映してしまえば先程と同じようにマージしてsvnにも反映させるだけです。

svnへ反映する人が複数欲しい場合

svn履歴をgitに移行した作業者以外はリモートのgitリポジトリからcloneしているはずです。

その場合、ローカルリポジトリにsvnの履歴なくsvnに変更を反映ができません。

作業者全員がgit svn fetchを何時間も待たなければいけない?
いいえ、そんな必要はありません。

git clone git@host:repo
git svn init --prefix=svn/ https://example.com/svn/repo --trunk=/trunk/repo
git update-ref refs/remotes/svn/trunk master
git svn fetch

こうすればtrunkとmasterを紐づける事ができます。
git svn fetchも一瞬で終わるはずです。

第二段階の移行作業

場合によってはここからが本番です。

すぐに切り替えができない原因の討伐を始めましょう。

  • 老害の説得
  • 開発ドキュメントの整備
  • git移行の周知
  • チームで最低レベルを合わせる
  • ビルド環境の移行
  • gitでのリリース管理

チームによって必要な作業、かかる時間はそれぞれ違います。
徐々にsvnからgitへ移行してもらい全員がgitでの開発に移行できるまで、勉強会やドキュメント整備を続けましょう。
svnとgitで双方向に変更を反映できるようにしたのもそのためです。

第三段階の移行作業

svnが不必要になる頃合いを見計らいましょう。
失敗するとsvn勢の開発継続が難しくなるのでくれぐれも慎重に。

まずsvnで開発している人が誰もいないことを確認しましょう。
svnの変更がないことを確認して、もしあればgitに反映しましょう。
最後かと思うとgit svn rebaseも名残惜しいですね。

ついにsvn鯖をぶっ壊す時が来ました。
万が一のため事前にsvnadmin dumpでバックアップを取得するなどするべきですが、私は行っていないです。
物理破壊でもリポジトリ削除でもsvnにコミットできないようにできれば方法は問いません。

おしまい

段階的に移行すれば移行のハードルはかなり低くなります。
まずgitでの開発環境を整備して、git至上主義者の味方を徐々に増やしましょう。
svnを駆逐して幸せなgitでの開発ライフを!

Discussion