サブモジュールの注意事項
サブモジュール使用時の注意事項です。チェックアウト方法が2種類ある
「サブモジュール」のチェックアウト方法には、以下の2種類があります。- スーパープロジェクトからサブモジュールをチェックアウトする
- サブモジュールでチェックアウトする
1.スーパープロジェクトからサブモジュールをチェックアウトする
「スーパープロジェクト」から「サブモジュール」をチェックアウトします。この時、「スーパープロジェクト」が管理している「サブモジュール」の「コミットID」が指す「コミットオブジェクト」から、プロジェクトのファイル群をチェックアウトします。
2.サブモジュールでチェックアウトする
「サブモジュール」でチェックアウトします。この方法は通常のリポジトリーでチェックアウトする方法と同じです。
従って、ユーザーが指定した「コミットオブジェクト」から、プロジェクトのファイル群をチェックアウトします。
どちらのチェックアウト方法を選ぶか
「サブモジュール」クローン時は、「1.」の方法によるチェックアウトが行われますが、クローン後は「1.」の方法でも「2.」の方法でもチェックアウトが可能です。「サブモジュール」クローン後は、ユーザーにとって都合の良い方法でチェックアウトを行ってください。
コミットIDが存在しない場合は
「サブモジュール」を追加する際、「サブモジュール」のクローンが行われチェックアウトが実行されます。この時「スーパープロジェクト」に、追加した「サブモジュール」の「コミットID」が存在しないため、通常のリポジトリー同様に「HEAD」(現在のブランチ)からチェックアウトされます。
スーパープロジェクトからサブモジュールをチェックアウトすると、分離したHEADになる
「スーパープロジェクト」から「サブモジュール」をチェックアウトすると、「サブモジュール」の「HEAD」は、「分離したHEAD」になります。これは「コミットID」が「コミットオブジェクト」を直接指しているためです。
ユーザーは必要に応じて「サブモジュール」でチェックアウトすることも可能です。
分離したHEADのまま作業しない
もし「サブモジュール」で、「ワーキングディレクトリー」内のファイルの編集を行いコミットする場合は、「分離したHEAD」の状態のまま、コミットしないでください。必ず事前に「サブモジュール」でチェックアウトを実行し、「HEAD」が既存のブランチを指すようにするか、「分離したHEAD」が指す「コミットオブジェクト」を起点にブランチを作成してから、コミット作業を行ってください。
さもないと、コミットで生成した「コミットオブジェクト」にアクセスできなくなります。
これは「サブモジュール」から見たら、到達できない「コミットオブジェクト」になるためです。
「サブモジュール」は「コミットID」の存在を知りません。
一方、「サブモジュール」のプロジェクトのファイル群を参照するだけなら、「分離したHEAD」のままでも問題ありません。
コミットIDの適切な更新とリモートリポジトリーへの反映
ユーザーは「コミットID」を適切に更新する必要があります。また、更新した「コミットID」を適切に「リモートリポジトリー」に反映する必要があります。
さもないと、別のユーザーが「サブモジュール」をクローンする際、「サブモジュール」のチェックアウトに失敗したり、意図しない「コミットオブジェクト」からチェックアウトすることになります。
他のユーザーの混乱の元になるため、「スーパープロジェクト」を管理するユーザーは、「サブモジュール」の「コミットID」の管理に注意を払う必要があります。
スーパープロジェクトをリモートリポジトリーに反映しても、サブモジュールはリモートリポジトリーに反映されない
「スーパープロジェクト」をプッシュして「リモートリポジトリー」に反映しても、自動的に「サブモジュール」のプッシュ及び「リモートリポジトリー」への反映は行われません。それぞれ個別に「リモートリポジトリー」への反映が必要になります。
サブモジュールの反映を先に行う
「サブモジュール」でコミットを行い、「スーパープロジェクト」で更新した「コミットID」をコミットしたら、まず「サブモジュール」をプッシュして「リモートリポジトリー」に反映します。次に「スーパープロジェクト」をプッシュして「リモートリポジトリー」に反映します。
サブモジュールのクローンに失敗するケース
「コミットID」の更新と「サブモジュール」のクローンに失敗するケースを上げてみます。1.サブモジュールでコミット
ユーザーAが、「サブモジュール」で編集を行いコミットを実行しました。2.スーパープロジェクトでコミット
ユーザーAが「サブモジュール」の「コミットID」を更新するため、「スーパープロジェクト」でコミットを実行しました。3.スーパープロジェクトのプッシュ
ユーザーAが「スーパープロジェクト」をプッシュし、「スーパープロジェクト」の「リモートリポジトリー」に更新した「コミットID」を反映しました。この時ユーザーAが、「サブモジュール」のプッシュを忘れ、「サブモジュール」の「リモートリポジトリー」に「サブモジュール」で行ったコミットを反映しなかったとします。
4.リポジトリーのクローン
別のユーザーであるユーザーBが、「スーパープロジェクト」をクローンし、「サブモジュール」のクローン及びチェックアウトを実行しました。この時、「コミットID」が指す「コミットオブジェクト」が見つからず、以下のようにエラーになります。