Python の構成管理ツールを Mercurial に移行
mercurial-ja でも話題を振ったけど、一応こちらでも。
Python 自身の開発に使用する構成管理ツールを、Mercurial に移行することが決定(英語)した模様。
決定の過程に関する詳細は、http://www.python.org/dev/peps/pep-0374/(英語) などからみることが可能。
上記の選出過程詳細における Tests/Impressions を見ると結構面白くて:
VCS | San Francisco | Vancouver | Space |
---|---|---|---|
svn | 1:04 | 2:59 | 139 M |
hg | 2:30 | 5:24 | 171 M |
git | 2:54 | 5:28 | 134 M |
上記テーブルは、Python リポジトリからの clone(checkout) に要する時間/ディスク消費なのだけど、全履歴情報を保持している筈の git が、Mercurial どころか svn よりもディスク消費量が少ない!
「Mercurial に比べて耐障害性が高い」理由が「差分保持じゃなくて、リビジョン毎の全スナップショット保持」だった筈なのに、その上でディスク消費が少ないっておかしくない?という疑問は、その先に書かれている『履歴表示』や『特定リビジョンへの update』の所要時間を見れば氷解。
おそらく猛烈に圧縮してあるんだね。clone で git の所要時間が多いのも圧縮処理に時間を要しているのかな。
※ 2014/01/28 追記
選定時の評価対象となった Git 1.6.1 の時点で、履歴データを単一ファイル化する pack 形式が導入されているので、単純な「データ圧縮率」ではなく、以下のような理由により、ディスク消費量が少なくなっているのだと思われます。
Git の checkout 性能が低いのは、pack 形式からのデータ取り出し自体(and/or 差分記録された場合の必要なデータの展開)がコスト高なのかもしれません。
ちなみに、ファイルの初期追加で Git/Mercurial の単一データ圧縮を比較したところ、Git よりもむしろ Mercurial の方が若干データ圧縮率が高めでした。
pack 時における共通データ部分の共有
Git の pack 形式では、類似性の高いファイルを記録する際に、元データ+差分の形態で記録されるため、ディスク消費量が低減される模様です。
pack 形式化は、明示的な git gc
実行をはじめとする garbage collection 契機で実施されるため、pack 化される前の状態だと、ディスク消費の傾向が変わる可能性もあります。
Mercurial の場合、履歴情報記録において、ファイル内容をファイル横断で共有するようなことが無い為、内容が同じ/類似性が高いファイルが多数あるようなケースでは、ディスク消費量の差が、より顕著になるかもしれません。
単一 pack ファイル化による、ブロック消費量の削減
Mercurial のリポジトリでは、個々のファイル内容の変遷は、記録先がファイル毎に分かれています。そのため、HDD の消費ブロック数ベースでのリポジトリサイズは、本来のデータサイズ以上に上振れする傾向があります(データサイズ << ブロック消費)。
例えば、Linux の ext3 ファイルシステムのデフォルトでは、ブロック割り当て単位は 4096 バイトです。つまり、10 バイトのファイルでも、4095 バイトのファイルでも、消費ブロック数ベースでは 4096 バイト分だけ消費することになります。
その一方、履歴が pack 化(= 単一ファイル化)された Git リポジトリでは、そういった上振れ分がありません(データサイズ ≒ ブロック消費)。
仮に、個々のファイルで見れば僅かな誤差しかなかったとしても、一定以上の規模(= 管理対象ファイル)を持つリポジトリの場合、データサイズとブロック消費の乖離は、無視できない量になる可能性があります。