git submodule
目录
git submodule
git 模块允许以一种更优雅的方式在你的 git 项目中嵌套一个子 git 项目
bash
# 添加子模块
git submodule add <url> [<path>]
# 初始化
git submodule init
# 更新
git submodule update
# 或者合二为一
git submodule update --init
# 使用 --recursive 嵌套初始化子子模块
git submodule update --init --recursive
# 或者直接在 clone 父仓库时初始化
git clone --recurse-submodules <url>
变更
父项目不会记录子项目中的文件修改,只有在子项目更新版本(git pull,checkout 等)时,会将子项目的版本修改记作为父项目的一条变更,如下:
bash
git commit -am 'added DbConnector module'
[master fb9093c] added DbConnector module
2 files changed, 4 insertions(+)
create mode 100644 .gitmodules
create mode 160000 DbConnector
注意 DbConnector 记录的 160000 模式。 这是 Git 中的一种特殊模式,它本质上意味着你是将一次提交记作一项目录记录的,而非将它记录成一个子目录或者一个文件。
子模块的版本更新后,更新记录随着 commit 提交到父项目。这样,当父项目变更(如 checkout)版本时,子项目也会随之变更到对应的版本。
子项目跟随父项目更新之后可能不会导致子项目内的文件(抓取但不覆盖),可以添加--recurse-submodules
来让子模块也随之修改到对应的版本,也可以使用git submodule update
来更新子模块
使用 git diff
/ git status
或者 IDE 的默认 git 无法查看子项目的具体文件变更,需要添加--submodule
参数。如果你不想每次运行 git diff 时都输入 --submodule
,那么可以将 diff.submodule 设置为 “log” 来将其作为默认行为。
bash
$ git status
On branch master
Your branch is up-to-date with 'origin/master'.
Changes not staged for commit:
(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)
modified: .gitmodules
modified: DbConnector (new commits)
.gitmodules
本质上就是在 git 项目里面添加一个文件夹放子项目(真的吗?),但是通过位于项目根目录下的.gitmodules
(git submodule add
之后自动生成)可以优雅地管理子项目
不用写.gitignore
来屏蔽子项目文件夹,同时 git 命令也能识别子项目
.gitmodules
[submodule "DbConnector"]
path = DbConnector
url = https://github.com/chaconinc/DbConnector