Skip to content

Git サブモジュールと大規模リポジトリ

はじめに

サブモジュールは 1 つの Git リポジトリ内に別のリポジトリを埋め込む仕組み。強力だが運用摩擦も生む。ここでは適用判断・管理方法・大規模構成の代替策を説明する。

使うべき/避けるべき場面

適合不適合
共有ライブラリのバージョン固定高頻度な双方向変更
外部依存のベンダリング密結合かつ同時変更要求
法務/監査で独立性必要フロー未習熟の開発者多数

追加

bash
git submodule add https://github.com/vendor/lib-a external/lib-a
git commit -m "Add lib-a submodule"

.gitmodules が生成。

.gitmodules 例

[submodule "external/lib-a"]
  path = external/lib-a
  url = https://github.com/vendor/lib-a

クローン

bash
git clone https://github.com/org/app.git
cd app
git submodule update --init --recursive

一括:

bash
git clone --recurse-submodules <url>

更新

bash
cd external/lib-a
git fetch
git checkout v2.4.0
cd ../..
git add external/lib-a
git commit -m "Bump lib-a to v2.4.0"

git diff --submodule で要約。

削除

bash
git submodule deinit -f external/lib-a
rm -rf .git/modules/external/lib-a
git rm -f external/lib-a
git commit -m "Remove lib-a submodule"

ピットフォール

問題原因緩和
サブモジュール内 detached HEAD初期状態変更するならブランチ作成
ポインタ更新忘れサブモジュール内だけ commit親 repo でパスを stage
ネスト混乱多段サブモジュール--recursive or 構造簡素化
.gitmodules 競合並行編集早期 rebase / 調整

大規模 Monorepo 代替

戦略説明
Monorepo単一履歴 + 共通ツール
Subtreeメタデータ過少で外部コード取り込み
パッケージマネージャRegistry 配布
複数 repo + CI オーケストレーション分離管理と自動連携

Subtree 簡易例

bash
git subtree add --prefix=vendor/lib-a https://github.com/vendor/lib-a main --squash

更新:

bash
git subtree pull --prefix=vendor/lib-a https://github.com/vendor/lib-a main --squash

パフォーマンス Tips

  • CI 浅クローン: git clone --depth 20
  • 部分クローン (Git 2.19+):
bash
git clone --filter=blob:none --sparse <url>
  • Sparse checkout:
bash
git sparse-checkout init --cone
git sparse-checkout set src/ docs/

状態監査

bash
git submodule status --recursive

セキュリティ

  • ソースをレビュー(ビルドで実行される)
  • 動くブランチでなく tag/commit 固定
  • サプライチェーン警告監視

まとめ

サブモジュールは明示的なバージョン固定に有効だが摩擦も伴う。用途を明確にし、広範統合要件には subtree / パッケージ / monorepo を評価せよ。

次へ

  • 自動化 (git-hooks-and-automation.md)
  • チーム協業 (git-best-practices-for-team-collaboration.md)

主要コマンド

bash
git submodule add <url> <path>
git submodule update --init --recursive
git diff --submodule
git submodule status --recursive