バージョン管理
ファイル管理のライフサイクル
- ファイル(リソース or プロジェクト)を作る。レポジトリを作成する。
- CVSでは最初にファイルをインポートして、チェックアウトして、それを作業ファイルとして使う。
- GITでは作業ディレクトリを作って、そのディレクトリをレポジトリとして初期化する。
- 分散環境のGITでは親レポジトリを作成する。作業ファイルを含まない bare repository の場合もある。
- リポジトリと結び付けられた作業ファイルを作る。
- CVSではレポジトリをチェックアウトして、それを作業ファイルとして使う。
- 分散環境のGITではレポジトリの複製を行い、レポジトリから作業ファイルを取り出す。
- 作業ファイルを使う(更新する)
- 作業ファイルの更新をレポジトリに書き戻す
- CVSではレポジトリにコミットする。
- 分散環境のGITではレポジトリそのものの差分をpushによって書き戻す。
- 作業ファイルを消す
安全に作業ファイルを捨てることがバージョン管理の目的のひとつではないか。
作業ファイルとレポジトリをリンクさせて合理的に管理するためにバージョン管理システムを使用する。
CVS
CVS におけるレポジトリはファイルが単位である。 レポジトリは(グローバルにユニークな)サーバ上のファイル(RCS形式を拡張したデータ形式)で存在し、 レポジトリの位置はサーバ上のファイルのパスとして指定される。 あらゆる作業ファイルは、どこかにある(ファイルとしての)レポジトリに対応する。 コミットは一つ一つのファイルの変更に対して個別に実行される。 ファイルとしてのリポジトリには、複数のリビジョン(1.xxのようなリビジョン番号で指定される)が存在する。 タグおよびブランチによってリビジョン番号の参照が容易になる。ブランチによってリビジョンは枝分かれする。
Subversion
Subversion (SVN) におけるレポジトリはファイルが単位である。(と言い切ってよい?) あるファイルに対応するレポジトリの実体は、個別のファイルとしては存在しない。 一つのレポジトリは複数のファイルをまとめて管理する独自のファイルフォーマットとして存在する。 レポジトリの中でのディレクトリ階層は、ブランチの名前を表すこともある。 コミットは複数のファイルの変更に対してまとめて実行され、リビジョン番号はレポジトリ全体に対して通し番号で付与される。
GIT
GIT におけるレポジトリは、作業ディレクトリ(プロジェクト)に対応する。 通常、作業ディレクトリに .git というサブディレクトリを作成してレポジトリとして使う。 一つのレポジトリにはファイルやサブディレクトリを含むことができる。 部分的に内容が異なる複数の作業ディレクトリを作成する代わりに、作業ディレクトリの状態を切り替えるためのブランチ機能が利用できる。 複数のユーザでレポジトリを共有する場合には、「誰が(どこで)保持している」「どのプロジェクトの」 「どのブランチ・どのタグの」ファイル群であるかが意識される。 コミットは複数のファイルの変更に対してまとめて実行され、リビジョン番号はハッシュ文字列として付与されるので、グローバルにユニークである。
- ソーシャル化するOSS開発者たち http://www.atmarkit.co.jp/news/analysis/200904/14/git.html
- 「ブランチを作ることなんて問題じゃない。マージこそが重要なんだ」
GIT では commit のときにコメントを省略できない。 (CVSでは -m "" で空のコメントを与えることができた) 例えば github.com ではファイルと一緒に「最後にコミットしたときのコメント」が表示される。 そのため、GIT では「定期的にスナップショットをコミットする」という考え方よりも、 意味的なまとまりごとに変更をコミットして、コミットのコメントと変更されたファイルの 対応関係に意味を持たせることが好ましいと考えられる。
ひとりごと
2003年ごろ西本が radiofly.to/wiki に執筆した記事を転載します。
* バージョン管理について by nishi **2003-05-04 開発やデバッグといった作業に疲れると、 こんな感じで現実逃避をしてしまう自分。 -ときどき開発をがんばる -ときどき「なぜ疲れるのか」「どうやったら楽になるのか」を考える [[バージョン管理システムCVS:http://radiofly.to/nishi/cvs/]] に限らず、 [[過去のコンテンツ:http://radiofly.to/nishi/]] はほとんど、 そうやって仕事の合間に書きためた。 だから、 [[CVSの本:http://radiofly.to/nishi/cvsbook/]] を書くような作業は、 本当は自分は適役だったかどうか、自信がない。 とは思うものの、最近また、 新しく何か言うべきことがあるかどうか、 考えてみようと思いはじめた。 **バージョン管理はめんどくさいか めんどくさい。おっしゃるとおりです。 だから、 「このとおり操作してください」 というマニュアルが必要だった。 しかし、 「バージョン管理をもっと簡単にできるのか?」 という問いには、 あまりよい答がない。 もしかしたら、 本質的に「めんどくささ」に 価値があるのではないか、 とさえ思っている。 (CVS本のあとがきにちょっと書きましたが) キーボード主体のコマンド操作のめんどくささと、 それに馴れたときの心地好さを、 僕は「茶道のお点前」のように感じたことがある。 -[[提言]] [[方法の冒険]] 参照 **危険を犯すためには方法が必要 バージョン管理には 「危険を犯すための秘術」 という側面がある。 例えば、つくりかけのソフトに対して、 次のように思ったらどうするか? -もしかしたら動かなくなるかも、でも改造して機能を追加したい -もしかしたら戻し方がわからなくなるかも、でもすっきり構造を整理したい CVSの Concurrent というのは、 そういう場合のための「秘術」だと言える。 そんな「危険」な作業が、 「めんどくささ」 を伴っていないのは、かえってやばくないか? **バージョン管理の詳細はなぜ語られにくいか バージョン管理の話には、 どうも下ネタを語るような気恥しさがある。 例を出そうとすると、 自分が関っている プロジェクトの具体的な ソースファイルの名前や ソースコードの断編が出てきがちである。 オープンなメーリングリストで議論するときに、 コンフィデンシャルな部分を 捨象して質問しなくてはならない。 そういう意味で、 Mozilla などのオープンソースプロジェクトは 貴重なケーススタディである。 また、ソフトウェア構成管理に関する本は 読んでいて面白い。 僕は最近 Mozilla Mail はなぜ APOP に 対応しないのか知りたくて mozilla.org で bugzilla を見てみた。 bugzilla のログを追いかけると、 1つのバグやpatchをめぐって どんな議論があるのか、 なかなか興味深い。 **2003-05-07 ***current と stable を使い分ける開発作業 -ひとつのリポジトリを2箇所にチェックアウトする (hoge-stable, hoge-current) -hoge-stableは,確実に動く状態を保持するように,ときどき cvs update -d --tag を打ちたくなるリビジョンの候補となる -hoge-currentは,日々の作業のロールバック対策 ロールバックの詳細 ***Debug build と Release build **TIPS / FAQ $ cvs update -d ** RCS 実は RCS を真面目に覚えないで CVS を覚えてしまった。 どういうときに RCS を使えばよく, どういうときに CVS を使ったほうがよいのか,分かりやすい説明方法を考えてみる。 -[[The RCS MINI-HOWTO:http://www.linux.or.jp/JF/JFdocs/RCS.html]] ** GUIRCS -[[GUIRCS:http://www.vector.co.jp/soft/win95/prog/se153965.html]] (Vector) 啓蒙活動には GUI が必要である。 (なんでだろう?)