我有一个工作项目如下:
project/
.git/
.gitmodules
submodule/ # submodule is a git submodule
Run Code Online (Sandbox Code Playgroud)
我希望,每当我在子模块中进行提交时。父模块将使用相同的提交消息project进行提交。submodule我尝试使用commit-msg钩子来实现这个:
#!/bin/bash
# project/.git/modules/submodule/hooks/commit-msg
cd $(dirname ${BASH_SOURCE[0]})/../../../..
git commit submodule -m "$(cat $1)"
Run Code Online (Sandbox Code Playgroud)
但这不起作用,因为我收到错误消息“错误:pathspec '子模块'与 git 已知的任何文件不匹配”。原因似乎是因为git commit命令也会调用commit-msg钩子,导致递归调用。
我可以知道我应该如何正确地执行此操作吗?
commit-msg可能不是执行此操作的最佳位置,因为它用于处理提交消息,并且在调用它时尚未进行子模块提交。
这个post-commit钩子对我有用:
COMMIT_MSG=$(git log -1 --pretty='format:%B' HEAD)
# I use zsh so $0 works for me. In bash BASH_SOURCE is correct
TOP=$(realpath $(dirname $0)/../../../..)
GIT_INDEX_FILE_SAV=$GIT_INDEX_FILE
unset GIT_INDEX_FILE
git --git-dir .git --work-tree . -C ${TOP} commit sub -m "${COMMIT_MSG}"
GIT_INDEX_FILE=$GIT_INDEX_FILE_SAV
Run Code Online (Sandbox Code Playgroud)
当钩子被调用时,我们处于git commit子模块的中间,因此GIT*根据子模块存储库设置各种环境变量。我们需要重置它们并让 git 使用父存储库中的值。
[编辑] 更好的填充方法$TOP是
TOP=$(git rev-parse --show-superproject-working-tree)
Run Code Online (Sandbox Code Playgroud)
感谢@phd 的建议。