使用预提交搜索文件

时间:2014-07-26 06:09:45

标签: git terminal grep pre-commit-hook

我正在尝试添加一个git预提交钩子,它将检查TODO:文本的所有已更改和新文件。

我试过

#!/bin/sh

. git-sh-setup  # for die 
git-diff-index -p -M --cached HEAD -- | grep '^+' |
grep TODO: && die Blocking commit because string TODO: detected in patch
:

我在类似的问题中看到了,但没有运气。

2 个答案:

答案 0 :(得分:9)

首先,钩子必须位于.git/hook文件夹中并且名称为pre-commit(执行权限为chmod +x .git/hooks/pre-commit

OP jesusjjf确认问题in the comments

  

我已将pre-commit.sample文件中的内容复制到纯文本文件中,而不是仅重命名。

其次,这是一些脚本示例:


You have another example使用类似技术,使用git rev-parsegit diff-index以及empty tree I mentioned before

#!/bin/sh

if git rev-parse --verify HEAD >/dev/null 2>&1; then
    against=HEAD
else
    against=4b825dc642cb6eb9a060e54bf8d69288fbee4904
fi

for FILE in `git diff-index --name-status $against -- | cut -c3-` ; do
    # Check if the file contains 'debugger'
    if [ "grep 'debugger' $FILE" ]
    then
        echo $FILE ' contains debugger!'
        exit 1
    fi
done
exit 

The comments on this gist提到:

在我的系统上,if [ "grep 'debugger' $FILE" ]始终评估为true 将其更改为if grep -q 'debugger' "$FILE"可修复该问题。


A more recent example

#!/bin/bash

# Pre commit hook that prevents FORBIDDEN code from being commited.
# Add unwanted code to the FORBIDDEN array as necessary

FILES_PATTERN='\.(rb|js|coffee)(\..+)?$'
FORBIDDEN=( debugger ruby-debug )

for i in "${FORBIDDEN[@]}"
do
  git diff --cached --name-only| grep ".js" |xargs sed 's/ //g'|grep "ha_mobile.debug=true" && \
        echo 'COMMIT REJECTED Found ha_mobile.debug=true references. Please remove them before commiting' && exit 1

  git diff --cached --name-only | \
        grep -E $FILES_PATTERN | \
        GREP_COLOR='4;5;37;41' xargs grep --color --with-filename -n $i && \
        echo 'COMMIT REJECTED Found'  $i 'references. Please remove them before commiting' && exit 1
done

exit 0

答案 1 :(得分:7)

这个位循环播放的文件,是的,然后它会影响整个文件而不管它的哪些部分被暂存!

   git diff --cached --name-only | \
       grep -E $FILES_PATTERN | \
       echo 'COMMIT REJECTED Found'  $i 'references. Please remove them before commiting' && exit 1

这不好 - 不要测试没有上演的字符串。

此解决方案针对仅针对已暂存的代码而非整个文件测试一个或多个FORBIDDEN字符串:

预提交

#!/bin/bash

RESTORE='\033[0m'
RED='\033[00;31m'
YELLOW='\033[00;33m'
BLUE='\033[00;34m'

FORBIDDEN=( 'TODO:' 'DO NOT COMMIT' 'console.log' 'die' )
FOUND=''

for j in "${FORBIDDEN[@]}"
do
  for i in `git diff --cached --name-only`
  do

    # the trick is here...use `git show :file` to output what is staged
    # test it against each of the FORBIDDEN strings ($j)

    if echo `git show :$i` | grep -q "$j"; then

      FOUND+="${BLUE}$i ${RED}contains ${RESTORE}\"$j\"${RESTORE}\n"

    fi
  done
done

# if FOUND is not empty, REJECT the COMMIT
# PRINT the results (colorful-like)

if [[ ! -z $FOUND ]]; then
  printf "${YELLOW}COMMIT REJECTED\n"
  printf "$FOUND"
  exit 1
fi

# nothing found? let the commit happen
exit 0

enter image description here