我有一个git pre-commit hook,它可以确定linting。当它被调用时,它循环遍历文件并在它们上运行一个linter。这很好。如何判断git是否在预提交钩子中使用“-a”标志执行?
但是,当您运行git commit -am 'Foo'
它运行时没有任何分阶段文件。我如何判断它是否被-a
或--all
标志调用?有没有更容易的方法来获取将存储在git中的文件?
我有一个git pre-commit hook,它可以确定linting。当它被调用时,它循环遍历文件并在它们上运行一个linter。这很好。如何判断git是否在预提交钩子中使用“-a”标志执行?
但是,当您运行git commit -am 'Foo'
它运行时没有任何分阶段文件。我如何判断它是否被-a
或--all
标志调用?有没有更容易的方法来获取将存储在git中的文件?
全部索引中的文件将被存储。您正在查找“索引中与HEAD
中的文件不同的文件”,您可以通过git diff
找到这些文件,或者查找脚本git diff-index
。
请注意,分阶段版本可能会不同于工作树版本,使检查一切特别恼人和棘手。 (举一个例子,在某些复杂的变化运行git add -p
,并选择它部分。)
这里的一个虚设pre-commit钩子的一个例子,显示名称和每个文件的状态相对于HEAD
,即,该指数与现有的HEAD
承诺有什么不同。
#! /bin/sh
git diff-index --cached -r --name-status HEAD
echo pre-commit fail
exit 1
你的任务是采取从git diff-index --cached -r --name-status HEAD
输出(也许-z
补充说,也许不是),并找出如何测试在索引中的版本,而不是在工作树的版本。
请注意,您可以使用git checkout-index
将索引提取到工作树。当然,你要避免覆盖真正工作树,即在其他地方建立一个临时的工作树:
TMPTREE=$(mktemp -d)
...
git --work-tree=$TMPTREE checkout-index -- .
例如。您可能需要建立一个临时的指数,比一般的指数,这个其他为好,因为这可能会干扰常规的索引缓存方面:
TMPINDEX=$(mktemp)
NORMINDEX=${GIT_INDEX_FILE:-$(git rev-parse --git-dir)/.index}
cp $NORMINDEX $TMPINDEX
GIT_INDEX_FILE=$TMPINDEX GIT_WORK_TREE=$TMPTREE checkout-index -- .
一定要清理临时文件和/或目录完成后。
(这些代码片段都没有经过测试。)
你所描述的不是这种情况。但是,如果你调用'commit',那么预先提交就会被设置为将被提交的内容,并且适当地设置'HEAD',这样你就可以'git diff --cached --name-only'或者其他任何你需要的东西做。 –
我正在使用'pygit2'。当我使用unstaged文件调用'repo.status()。items()'时,我得到如下所示的结果:'[('config/git_hooks/pre-commit',256),('bin/run_flake8',256)] '。 '256'是GIT_STATUS_WT_MODIFIED的标志。 –
我还没有看过pygit2(我写了自己的Python Git回到了git 1. [567],python 2. [345]时代,但那是几个职位以前,可能长期被丢弃),但它值得注意'git status'不会*两个*差异,一个用于索引-vs-HEAD,另一个用于worktree-vs-index。 Pygit2可能会尝试做同样的事情,但是如果是这样的话,它会出错,如果你是在你的预提交钩子内执行并运行'git commit -a'。 – torek