git hooks


hooks是一些在$GIT_DIR/hooks目录的脚本,在被特定的事件(certain points)触发后被调用。当git init命令被调用后,一些常用的示例钩子文件被拷贝到新仓库的hooks目录中;但是默认这些钩子时不生效的。把.sample后缀去掉之后生效。
1. applypatch-msg
GIT_DIR/hooks/applypatch-msg
当'git-am'命令执行时,这个钩子就被调用。 它只有一个参数:就是存有提交消息(commit log message)的文件的名字。如果钩子的执行结果是非零,那么补丁(patch)就被应用(apply).
这个用于在其他地方编辑提交消息,并且可以把这些消息规范成项目的标准格式。它也可以在分析完消息后拒绝此次提交。默认会执行调用commit-msg 钩子。

 
2. pre-applypatch
GIT_DIR/hooks/pre-applypatch
当'git-am'命令执行时,这个钩子就被调用。它没有参数,并且是在一个补丁(patch)被应用后还未提交前被调用。如果钩子的执行结果时非零,那么刚才应用的补丁就不会被提交。
它用于检查当前的工作树,当提交的补丁不能通过特定的测试时就拒绝将它提交进仓库。

 
3. post-applypatch
GIT_DIR/hooks/post-applypatch
当'git-am'命令执行时,这个钩子就被调用。它没有参数,并且是在一个补丁被应用且在完成提交之后被调用的。
这个钩子的主要用途时通知提示,它并不会影响'git-am'的执行结果。

 
4. pre-commit
GIT_DIR/hooks/pre-commit
这个钩子被'git-commit'命令调用,而且可以通过在命令中添加\ --no-verify参数来跳过。这个钩子没有参数,在得到提交消息和开始提交前被调用。如果钩子执行结果是非零,那么'git-commit'命令就会中止执行。
此钩子可以用来在提交前检查代码错误(运行类似lint的程序)
当默认的'pre-commit'钩子开启时,如果它发现文件尾部有空白行,那么就会中止此次提交。
新版本的默认钩子有不同。

 
5. prepare-commit
当'git-commit'命令执行时: 在编辑器(editor)启动前,默认提交信息准备好后,这个钩子就被调用。
它有三个参数:第一个参数是提交消息文件的名字;第二个参数提交消息的来源,它可以是:()
如果钩子的执行结果是非零,那么'git-commit'命令就会被中止。

 
6. commit-msg
GIT__DIR/hooks/commit-msg
当'git-commit'命令执行时,这个钩子被调用;也可以在命令中添加\ --no-verify参数来跳过。这个钩子有一个参数:就是被选定的提交消息文件的名字。如这个钩子的执行结果时非零,那么’git-commit'命令就会中止执行。
这个钩子使提交消息更适当,可以用于规范提交消息使之符合项目的规范;如果它检查提交消息后,发现内容不符合规范,可以拒绝此次提交。
默认的'commit-msg'钩子启用后,它检查里面是否有重复的签名结束线(Signed-off by lines).如果找到它就是中止此次提交操作。

 
7. post-commit
GIT_DIR/hooks/post-commit
当'git-commit'命令执行时,这个钩子就被调用。它没有参数,并且时在提交完成后被调用。
这个钩子的主要用途是通知提示,它并不会影响'git-commit'的执行和输出。

 
8.pre-rebase
GIT_DIR/hooks/pre-rebase
当'git-rebase'命令执行时,这个钩子就被调用;主要目的时阻止不应该被rebase的分支被rebase(例如,一个已经发布的分支提交就不应该被rebase)

 
9. post-checkout
GIT_DIR/hooks/post-checkout
当'git-checkout'命令更新完整个工作树(worktree)后,这个钩子就被调用。这个钩子有三个参数:前一个HEAD的ref,新HEAD的ref,判断一个签出时分支签出还是文件签出的标识符(分支签出=1,文件签出=0).这个钩子不会影响'git-checkout'命令的结果。
这个钩子可以用于检查仓库的一致性,自动显示签出前后的代码的区别,也可以用于设置目录的元数据属性。

 
10.post-merge
GIT_DIR/hooks/post-merge
当'git-merge'命令执行或在本地'git-pull'执行后调用,有一个参数状态标识符。

 
11.pre-receive
GIT_DIR/hooks/pre-receive
当在本地仓库执行'git-push'命令时,服务器上远端仓库就会对应执行'git-receive-pack'命令,而'git-receive-pack'命令会调用pre-recevie钩子。在开始更新远程仓库上的ref之前,这个钩子被调用。钩子的执行结果(exit status)决定此次更新能否成功。
每执行一个接收操作都会调用一次这个钩子。它没有命令行参数,但是它会从标准输入读取需要更新的ref,格式如下:
SP SP LF
注: SP是空格,LF是回车。
<old-value>是保存在ref里的老对象的名字,<new-value>是保存在ref里的新对象的名字,<ref-name>就是此次要更新的ref的全名。如果是创建一个新的ref,那么<old-value>就是由40个0组成的字符串表示。
如果钩子的执行结果是非零,那么没有引用(ref)会被更新。如果执行结果为零,更新操作还可以被后面的<<update,'update'>>钩子所阻止。
钩子(hook)的标准输出和输入都会通过'git-send-pack'转发给客户端(other end),你可以把这个信息回显给客户端。

 
12. update
GIT_DIR/hooks/update
当用户在本地仓库执行'git-push'命令时,服务器上远端仓库就会对应执行'git-receive-pack',而'git-receive-pack'会调用update钩子。在更新远程仓库行的ref之前,这个钩子被调用。钩子的执行结果决定此次updae能否成功。
每更新一个引用(ref),钩子就会被调用一次,并且使用三个参数,要被更新的ref的名字,ref中那些前的对象名,ref中更新后的对象名。
如果update hook的执行结果时零,那么引用(ref)就会被更新。如果执行结果是否非零,那么'git-receive-pack'就不会更新这个引用。
这个钩子也可以用于防止强制更新某些refs,确保old object时new object的父对象。这样也就是强制执行'fast forward only' 策略。
它也可以用于跟踪(log)更新详情。但是由于它不知道每次更新的ref全体集合,尽管可以傻傻的每个ref更新就发送email;但是<<post-receive,'post-receive'>>钩子更合适。
在邮件列表上讲来另一种用法:用这个update hook实现细粒度权限控制。
钩子的标准输出和标准错误输出都会通过'git-send-pack'转发给客户端,可以把这个信息回显给客户端。

 

 
13. post-receive
GIT_DIR/hooks/post-receive
当用户在本地仓库执行'git-push'命令时,服务器上远端仓库就会对应执行'git-receive-pack'命令;在所有远程仓库的引用都更新后,这个钩子就会被'git-receive-pack'调用。
服务器端仓库每次执行接收操作时,这个钩子都会被调用。此钩子执行不带任何命令行参数,但是和<<pre-recevie,'pre-receive'>>钩子一样从标准输入读取信息,并且读取的信息内容也是一样的。
这个钩子不会影响'git-receive-pack'命令的输出,因为它时在命令执行完后被调用的。
这个钩子可以取代<<post-update,'post-update'>>钩子因为后者只能得到需要更新的ref的名字,而没有更新前后的对象的名字。
钩子的标准输出和标准错误输出都会通过'git-send-pack'转发给客户端,你可以把这个信息回显给客户端
默认的'post-receive'钩子是无效的,但是在git distribution contrib/hooks目录里有一个名为post-recevie-email的示例脚本,实现来发送commit emails的功能。
 

 
14. post-update
GIT_DIR/hooks/post-update
当用户在本地仓库执行'git-push'命令时,服务器上远端仓库就会对应执行'git-recevie-pack'。在所有远程仓库的引用都更新后,post-update就会被调用。
它的参数数目时可变的,每个参数代表实际被更新的ref
这个钩子的主要用途是通知提示,它并不影响'git-receive-pack'的输出。
'post-update'可以告诉我们哪些heads被更新来,但是它不知道head更新前后的值,所以这里不太适合记录更新详情。而<<post-receive,'post-receive'>>钩子可以得到ref(也可以说是head)更新前后的值,如果你要记录更详细的信息的话,可以使用这个钩子。
如果默认的'post-update'钩子启用的话,它们执行'git-update-server-info'命令去更新一些dumb协议(如http)所需的信息。如果你的git仓库是通过http协议来访问,那么你就应该开启它。
钩子的标准输出和标准错误输出都会通过'git-send-pack'转发给客户端,你可以把这个信息回显给客户端
此钩子没有参数但可以从stdin读取参数
shell脚本方式是
read oldrev newrev refname
echo "Old revision: $oldrev"
echo "New revision: $newrev"
echo "Reference name: $refname"
python 脚本方式
import sys
for fp in sys.stdin:
    print fp
 
15. pre-auto-gc
GIT_DIR/hooks/pre-auto-gc
当调用'git-gc --auto'命令时,这个钩子就会被调用。它没有调用参数,如果钩子的执行结果是非零的话,那么'git gc --auto'命令就
 
利用以上钩子自定义功能
一、主服务器和镜像服务器间的同步
    描述: 两台git服务器A和B,保证推送到A上的变更会同时推送到B上,反之亦然。gitolite暂用了部分钩子,选择post-update这个实现。
    问题:
        1. 需要配置ssh远程别名否则钩子推送会出错
        2. git push origin refs 这个对新增tag或分支及更新有效,对删除tag或分支无效
            错误信息: remote: error: src refspec refs/tags/dev2 does not match any.
           因为删除和新增及修改的命令格式不同,需要另作处理
 
16. post-recevie-email
这个钩子是用于在仓库更新后通知用的,被post-recevie钩子调用。它依赖的三个参数在*.git/config: hooks.envelopesender,hooks.emailprefix and hooks.maillinglist
这个钩子通常在/usr/share/doc/git-core/contrib/hooks目录下,或通过查看post-recevie.sample文件最后一行获得

 


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM