Git 用于在分支更改时更新 Git 子模块的挂钩
Git hook for updating Git submodule on branch change
我正在处理一些使用 Git 子模块的旧代码。该代码有几个正在积极使用的不同分支,不幸的是,这些分支中的每一个都依赖于相关子模块的不同修订版; this has made development extremely complicated。我面临的问题之一是,当我在分支之间切换时,例如master
到 newfeature-foo
使用 git checkout newfeature-foo
,子模块的状态保持在 master
的状态,这通常会导致编译错误,甚至更糟糕的是会导致运行时行为的差异,从而造成严重破坏通过用户测试和一般理智。
例如,给定 .gitmodules
配置:
[submodule "robotcontroller"]
path = robotcontroller
url = https://coolrobots.com/repos/robotcontroller
branch = master
ignore = dirty
- 提交 77d4697 时的分支
master
引用了 robotcontroller @ f57d1b3
- b38d29f 的分支
newfeature-foo
引用了 robotcontroller @ 60b27d4
- 位于 873639f 的分支
master
根本没有子模块 robotcontroller
- 301dca4 的分支
newfeature-foo
引用了 robotcontroller @ bdf5991
有没有办法使用 Git 挂钩强制自动完全重新检出 .gitmodules
文件中列出的所有子模块,当它在检出 "root" Git 存储库时发生变化?
听起来您的回购协议中发生了很多事情,使事情变得混乱。我们可以反复多次来找到有冲突的设置,但我会这样做:
去掉ignore = dirty
这只是隐藏了有用的信息——也许子模块没有彻底检出,因为它会覆盖文件。至少,在尝试对其进行任何操作之前确认子模块是干净的 - cd mysubmodule
和 git status
= clean
post-checkout
钩子删除 robotcontroller
并更新所有子模块。
#!/bin/sh
# post-checkout hook that update submodules
prev_HEAD=""
new_HEAD=""
new_branch=""
if [ "$new_branch" = 1 ]; then
if ! grep -Fq robotcontroller .gitmodules; then
rm -rf robotcontroller
fi
git submodule update
fi
exit 0
PS。根 Git 存储库的正确术语是 "superproject"。 :-)
我正在处理一些使用 Git 子模块的旧代码。该代码有几个正在积极使用的不同分支,不幸的是,这些分支中的每一个都依赖于相关子模块的不同修订版; this has made development extremely complicated。我面临的问题之一是,当我在分支之间切换时,例如master
到 newfeature-foo
使用 git checkout newfeature-foo
,子模块的状态保持在 master
的状态,这通常会导致编译错误,甚至更糟糕的是会导致运行时行为的差异,从而造成严重破坏通过用户测试和一般理智。
例如,给定 .gitmodules
配置:
[submodule "robotcontroller"]
path = robotcontroller
url = https://coolrobots.com/repos/robotcontroller
branch = master
ignore = dirty
- 提交 77d4697 时的分支
master
引用了robotcontroller @ f57d1b3
- b38d29f 的分支
newfeature-foo
引用了robotcontroller @ 60b27d4
- 位于 873639f 的分支
master
根本没有子模块robotcontroller
- 301dca4 的分支
newfeature-foo
引用了robotcontroller @ bdf5991
有没有办法使用 Git 挂钩强制自动完全重新检出 .gitmodules
文件中列出的所有子模块,当它在检出 "root" Git 存储库时发生变化?
听起来您的回购协议中发生了很多事情,使事情变得混乱。我们可以反复多次来找到有冲突的设置,但我会这样做:
去掉ignore = dirty
这只是隐藏了有用的信息——也许子模块没有彻底检出,因为它会覆盖文件。至少,在尝试对其进行任何操作之前确认子模块是干净的 - cd mysubmodule
和 git status
= clean
post-checkout
钩子删除 robotcontroller
并更新所有子模块。
#!/bin/sh
# post-checkout hook that update submodules
prev_HEAD=""
new_HEAD=""
new_branch=""
if [ "$new_branch" = 1 ]; then
if ! grep -Fq robotcontroller .gitmodules; then
rm -rf robotcontroller
fi
git submodule update
fi
exit 0
PS。根 Git 存储库的正确术语是 "superproject"。 :-)