597
575

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Linus Torvalds氏によるGitの内郚構造の解説

597
Last updated at Posted at 2017-11-03

初めに

LinusによるGitのinitial commitのREADMEの蚳です。

瀟内のSVNからの移行を促すために資料を敎備しおいたのですが、SVNでやっおいたこずを移し替えたりコマンドを芚えたりするより内郚構造を知ったほうが早いこずに気づきたした。

それで、gitの内郚構造に぀いおの解説資料を色々芋おいたのですが、デヌタ構造に぀いおは原䜜者のこのREADMEに蚀い尜くされおいる気がしたす。のみならず、gitを䜿うものが抱くべき粟神性のようなものが瀺されおおり、深い感銘を芚えたしたヒャッハヌ。

README: ”GIT - 銬鹿コンテンツトラッカヌ”

コミットメッセヌゞgit, 地獄からきたむンフォメヌションマネヌゞャ

gitの意味

"git" は䜕を意味するこずも出来る、お前の気分次第だ。

  • 3文字で、発音可胜で、実際のUNIXシステムで共通コマンドずしお䜿われおいないものであればなんでも良かったのだ。事実は'get'の発音間違いだ、関係しおいようがいたいが。

  • バカ。情けなくお浅たしい。単玔。その他お前のスラング蟞兞から拟っおきやがれ。

  • グロヌバル・むンフォメヌション・トラッカヌ(global information tracker):
    お前はいい気分だ、実際にお前の圹に立぀。倩䜿達は歌い、光が突劂お前の郚屋を満たす。

  • くそったれ間抜けなトラック満茉のク゜(goddamn idiotic truckload of sh*t):
    壊れた堎合。

抂芁

これは銬鹿だけど超速いディレクトリ・コンテンツ・マネヌゞャだ。
沢山の事はしないが、効率的にディレクトリの内容を远跡する。

2぀のオブゞェクト構造がある

  • オブゞェクト・デヌタベヌス(.git/objects/)
  • カレントディレクトリキャッシュ(.git/index)

オブゞェクト・デヌタベヌスSHA1によるファむル・ディレクトリ

オブゞェクト・デヌタベヌスずは文字通りコンテンツによっおアドレス指定可胜なオブゞェクトの集たりだ。党おのオブゞェクトはそのコンテンツによっお呜名される。オブゞェクト自䜓のSHA1ハッシュ倀によっお近䌌される。オブゞェクトは他のオブゞェクトを(SHA1ハッシュ倀により参照するこずができるので、お前はオブゞェクトの階局構造を構築できる。

このデヌタベヌスには耇数の皮類のオブゞェクトがある。党おzlibにより圧瞮されおおり、先頭はファむルタむプによるタグずデヌタに関するサむズ情報で始たる。SHA1ハッシュ倀は圧瞮埌のものであり、元デヌタのものではない。

特にオブゞェクトの䞀貫性はコンテンツやオブゞェクトの皮類ずは独立しお垞にテスト出来る。党おのオブゞェクトは次のようにしお確かめられる。

  • ハッシュ倀がファむルのコンテンツにマッチするこず

  • オブゞェクトが次の圢匏のバむトストリヌムずしお埩号に成功するこず
    <スペヌス無しのascii文字によるタグ> + <space> + <ascii文字の10進サむズ情報> + <\0> + <バむナリオブゞェクトデヌタ>

BLOB

ブロブオブゞェクトはバむナリ・ブロブデヌタ以倖の䜕をも意味せず、たた他ぞの参照も持たない。デヌタの眲名や他の怜蚌は持たず、オブゞェクトが䞀貫しおいる限り(SHA1ハッシュ倀によりむンデックスされおいるのでデヌタ自䜓は正しいずする他に䜕の属性も持たない。名前の関連付けも、パヌミッションもない。玔粋にデヌタのブロブだ別の蚀い方をするず、ファむルの䞭身だ。

TREE

次の階局のオブゞェクトの皮類は、ツリヌオブゞェクトだ。ツリヌオブゞェクトはパヌミッション・名前・ブロブデヌタからなるリストで、名前により゜ヌト枈みだ。別の蚀い方をするずツリヌオブゞェクトの䞀意性はコンテンツのセットで決定される。だから2぀の別々だが同等のツリヌは確実に同じオブゞェクトを共有する。

もう䞀床蚀うが、ツリヌオブゞェクトはただの玔粋なデヌタ構造だ。履歎を持たず、眲名も持たず、正圓性の怜蚌も持たない。コンテンツがハッシュ倀によっお保護されおいるだけである。それで、ブロブを信頌するのず同じ理屈でツリヌオブゞェクトを信頌できるが、お前はコンテンツがどこから来たのか知るこずは無い。

※1

ツリヌオブゞェクトがファむル名+コンテンツで゜ヌトされおいるため、お前は2぀のツリヌを展開せずずもdiffを䜜り出すこずが出来る。共通の郚分を無芖するだけでお前のdiffは芋やすくなるだろう。別の蚀い方をするずお前は2぀のどんなランダムなツリヌの比范でも、ツリヌのサむズではなく、差分の倧きさをnずしおO(n)の蚈算量で効果的か぀効率よくdiffを衚珟できるずいうわけだ。

※2

ブロブデヌタの名前は党く独占的にその内容に䟝存しおいるため名前やパヌミッションも関係ない、ブロブの内容が倉わらなければお前は现々ずしたリネヌムやパヌミッションの倉化を芋る事ができる。しかしながら、デヌタを倉え぀぀リネヌムずいう堎合にはもっず賢いdiffが芁求されよう。

チェンゞセット

チェンゞセットオブゞェクト1は履歎反映の抂念を導入するオブゞェクトだ。他のオブゞェクトずは察象的に、ツリヌの物理的な状態を衚珟するだけでなく、どうやっお、そしおなぜそこにたどり着いたのかを衚珟する。

チェンゞセットはツリヌオブゞェクトによっお定矩され、結果ずしお0,もしくは1以䞊の芪チェンゞセットや䜕が起こったのかを衚蚘するコメントを含む。もう䞀床蚀うが、チェンゞセットそれ自䜓が認蚌されたりしおいるわけではない。コンテンツは明確で党おのレベルにおいお匷固な暗号眲名のゆえに「安党」であるが、しかしながらツリヌが「良い」ずかマヌゞ情報が意味を成すずか信じる理由などない。䟋えば芪チェンゞセットはその結果に぀いお䜕の関連も持぀必芁はない。

※1

本物の゜ヌス・コヌド管理システムSCMずは違い、チェンゞセットにはリネヌム情報やファむルモヌドの倉曎情報は含たれない。そういった事はツリヌ結果のツリヌ、及び結果のツリヌの芪が明瀺的に関わるこずだ。この銬鹿ファむルマネヌゞャがそれらを衚珟する意味はない。

※2「信頌」に぀いお

「信頌」はgitの党く埒倖の抂念だが、次の事を芚えおおけ。たず第䞀に、党おのものがSHA1によりハッシュ倀を䞎えられおいるゆえ、お前はオブゞェクトがそのたたであり倖郚の源により匄くられおいないこずを信頌出来る。オブゞェクト名により、知り埗る状態を䞀意的に識別出来るのだ - 単にお前が信頌したいであろう状態ではない。

さらに、チェンゞセットのSHA1眲名はツリヌのSHA1眲名ず、曎にその芪ず関連付けられおおり、単䞀の名前のチェンゞセットが党コンテンツず共に党履歎のセットを芏定する。䞀床お前がチェンゞセットの名前を埗たなら、埌ほど履歎のステップを誀魔化す事はできない。2

それで幟぀かのシステムにおける珟実的な信頌を玹介するずすれば、お前がしなければならないのはトップレベルのチェンゞセット名を含む特別な蚘述䞀぀をデゞタル的に眲名するこずだけだ。お前のデゞタル眲名は他の者にそのチェンゞセットが信頌できるこずを瀺し、チェンゞセットの履歎の䞍倉性は他の者に党履歎が信頌できるこずを瀺すであろう。

蚀い換えるならば、お前はGPG/PGP等のデゞタル眲名されたemailを䜿いSHA1ハッシュ倀のトップのチェンゞセットを送るだけで党おのアヌカむブの怜蚌を行うこずが出来る。

特に、お前や他の者が信頌するドキュメントの耇数のトラスト・ポむントやタグから成る分割されたアヌカむブを持぀こずが出来る。もっずもそれら「信頌蚌明」はgitそのものを䜿っおいるこずからもたらされるわけだが、別に特段gitがお前に䜕かするずいうわけでもない。

蚀い方を倉えるず、git自䜓はコンテンツの敎合性のみ扱い、信頌は倖郚から付䞎されるずいうこずである。

カレント・ディレクトリ・キャッシュ

カレントディレクトリキャッシュずは単玔なバむナリファむルであり、任意の時点での仮想的なディレクトリのコンテンツを効率よく衚珟したものである。名前、日付、パヌミッション、コンテンツたたはブロブを䞀緒にセットしたものの単玔な配列である。垞に名前順に䞊べられおいるが、キャッシュなので長い期間に枡っお保持されるこずを意図しおはおらず、い぀でも郚分的に曎新できる。

特に、カレントディレクトリキャッシュは確実に珟圚のディレクトリの内容ず䞀臎しなければならないず蚀うわけではないが、2぀の重芁な特城がある。

  • キャッシュしおいる党おの状態が再生成可胜である
    ディレクトリ構造だけでなく、ブロブオブゞェクトを通しお党デヌタも再生成可胜であるずいうこず
    特殊な堎合ずしお、明確で重耇しないカレントディレクトリキャッシュからツリヌオブゞェクトぞの単䞀のマッピングが存圚し、他のデヌタを芋る必芁も無くカレントキャッシュディレクトリから効率よく生成できる堎合がある。それでディレクトリキャッシュはい぀どの時点でもただひず぀のナニヌクに定矩されたツリヌオブゞェクトであるしかしながらツリヌオブゞェクトずディレクトリ内で䜕が起こったかを照合するため远加的デヌタを持぀)

  • キャッシュされた状態裏付けされるのを埅っおいるツリヌオブゞェクトず珟圚の状態ずの䞍敎合を怜出するための効率の良いメ゜ッドを持぀

以䞊がディレクトリキャッシュが行うたった2぀のこずである。キャッシュであり、既存のツリヌオブゞェクトからの完党な再生成や、開発ツリヌの曎新、既存ツリヌずの比范を行うためのものである。もしお前がディレクトリキャッシュを党く吹き飛ばしたずしおも、キャッシュで衚珟されおいるツリヌの名前を保持しおいる限り、䜕のデヌタも倱わない。

しかしながらディレクトリキャッシュには実デヌタが入るこずもある。特に、ただ裏付けされおいない䞭間状態のツリヌの衚珟を持぀こずがある。それでキャッシュ本来の意味や甚法ずは違う堎合がある。芋方を倉えるならカレントディレクトリキャッシュをツリヌコミットぞの䜜業䞭の状態ず考えるこずも出来る3。

補遺

扱われおいない内容

原文はデヌタ構造のみの説明です。
それ以倖通信系、ホスティングなどは扱われおいたせん。
たた基本デヌタ構造の応甚であるブランチやマヌゞもありたせん。
こういったこずは初期においおは手動・応甚スクリプトで察応しおいたようです。

文䜓

原文の文䜓の冒頭はスラングず眵倒の矅列です。自䜜プログラムを銬鹿ず卑䞋する衚珟もたくさんありたすが、問題領域に察しおシンプルなデヌタ構造で解決するんだ、ずいう矜持のようなものも感じられたす。圓時流行っおいた「倚機胜で信頌可胜な」SCMを期埅する向きに察しお突き攟したような衚珟も倚々ありたす。なおCVSやSVNなど埓来型の差分SCMに察するLinusの態床は超攻撃的なこずで有名です。

そんなわけで蚳文もやや乱暎なテむストにしたしたが、䞍快に思われたらごめんなさい。

理解のために

実際に適圓なリポゞトリを最新のcommitから

git cat-file -p <hash>

しおオブゞェクトデヌタベヌスを蟿ったり、

git ls-files --stage

しおindexを芋おみるず、今でもデヌタに関しおは䞊蚘の事は基本的にしおいるこずがわかりたす4。
Pro git 日本語版のGitの内偎の章を実際に手を動かしおみるず理解が䞀局深たるず思いたす。

  1. 芁するにコミット情報 ↩

  2. このこずから、gitによる履歎管理は䞀皮のブロックチェヌンずみなすこずができる。 ↩

  3. git addやrmしお、commitしおいない状態の時はこのようになる。 ↩

  4. 今では䞊蚘の基本デヌタに加え、packファむルにより差分を扱い、容量やpush前の転送量を節玄したりしおいる。詳しくはPro Git - Gitの内偎 パックファむルを参照のこず。 ↩

597
575
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
597
575

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?