Git Hooks

什么是Git Hooks?

话说,如同其他许多的版本控制系统一样,Git也具有在特定事件发生之前之后执行特定脚本代码功能(从概念上类比,就与监听事件、触发器之类的东西类似)。
Git Hooks就是那些在Git执行特定事件(如commit、push、receive等)后触发运行的脚本。
按照Git Hooks脚本所在的位置可以分为两类:
1.本地Hooks,触发事件如commit、merge等。
2.服务端Hooks,触发事件如receive等。

Git Hooks能做什么?

Git Hooks是定制化的脚本程序,所以它实现的功能与相应的git动作相关;在实际工作中,Git Hooks还是相对比较万能的。下面仅举几个简单的例子:

  • pre-commit: 检查每次的commit message是否有拼写错误,或是否符合某种规范。
  • pre-receive: 统一上传到远程库的代码的编码。
  • post-receive: 每当有新的提交的时候就通知项目成员(可以使用Email或SMS等方式)。
  • post-receive: 把代码推送到生产环境。(这就是我想要做的)
    etc...

更多的功能可以按照生产环境的需求写出来。

Git Hooks是如何工作的?

每一个Git repo下都包含有.git/hoooks
这个目录(没错,本地和远程都是这样),这里面就是放置Hooks的地方。你可以在这个目录下自由定制Hooks的功能,当触发一些Git行为时,相应地Hooks将被执行。
这里是一个Git Hooks列表,现在如果觉得不是很明白,不用担心,以后我会继续讲:
applypatch-msg
pre-applypatch
post-applypatch
pre-commit
prepare-commit-msg
commit-msg
post-commit
pre-rebase
post-checkout
post-merge
pre-receive
update
post-receive
post-update
pre-auto-gc
post-rewrite

图中是我一个本地repo的git hooks示例。

如何开始使用Git Hooks?

好了,前面啰嗦一大堆,这里才是重点。
如图中所示的文件,是由本地执行的脚本语言写成的,尽管这些文件默认会是Shell Script,你完全可以给它替换成自己喜欢的Ruby,Python或者Perl。

关于这些脚本文件的命名,细心的读者就会发现图中的文件都是上面Git行为列表中列出的名称加上后缀.sample。没错就是这样,把那些文件的后缀去掉,或者以列表中的名字直接命名,就会把该脚本绑定到特定的Git行为上。
所以说,Git Hooks的正确操作方式是:写脚本。
Git Hooks脚本分类
Git Hooks脚本可以按照运行环境分为两类:本地Hooks与服务端Hooks。

  • Client Side
    也就是上面提到的本地hooks。 其实本地hooks还是占大多数的,可以给它们分成三类:
    commit hooks
    e-mail hooks
    其他

  • Commit Hooks
    与git commit相关的hooks一共有四个,均由git commit
    命令触发调用,按照一次发生的顺序分别是:
    pre-commit
    prepare-commit-msg
    commit-msg
    post-commit

其中,pre-commit是最先触发运行的脚本。在提交一个commit之前,该hook有能力做许多工作,比如检查待提交东西的快照,以确保这份提交中没有缺少什么东西、文件名是否符合规范、是否对这份提交进行了测试、代码风格是否符合团队要求等等。 这个脚本可以通过传递--no-verify参数而禁用,如果脚本运行失败(返回非零值),git提交就会被终止。
prepare-commit-msg脚本会在默认的提交信息准备完成后但编辑器尚未启动之前运行。 这个脚本的作用是用来编辑commit的默认提交说明。 该脚本有1~3个参数:包含提交说明文件的路径,commit类型(message, template, merge, squash),一个用于commit的SHA1值。这个脚本用的机会不是太多,主要是用于能自动生成commit message的情况。 不会因为--no-verify参数而禁用,如果脚本运行失败(返回非零值),git提交就会被终止。
commit-msg
包含有一个参数,用来规定提交说明文件的路径。 该脚本可以用来验证提交说明的规范性,如果作者写的提交说明不符合指定路径文件中的规范,提交就会被终止。 该脚本可以通过传递--no-verify参数而禁用,如果脚本运行失败(返回非零值),git提交就会被终止。
post-commit
脚本发生在整个提交过程完成之后。这个脚本不包含任何参数,也不会影响commit的运行结果,可以用于发送new commit通知。

需要注意到,这几个脚本并不会通过clone传到项目中,而且既然是完全运行在本地,那就无法完全保证验证能起到作用(可以随便修改),但为了保证一些项目的可靠性,还需要开发者们自觉遵守这些规则。

  • E-mail Hooks
    与git am
    相关的脚本由三个,均由git am
    触发运行,按顺序依次是:
    applypatch-msg
    pre-applypatch
    post-applypaych

如果在工作流中用不到这个命令,那也就无所谓了。不过,如果要用git format-patch命令通过Email提交补丁,这部分内容还是比较有用的。
applypatch-msg
脚本最先被触发,它包含一个参数,用来规定提交说明文件的路径。该脚本可以修改文件中保存的提交说明,以便规范提交说明以符合项目标准。如果提交说明不符合规定的标准,脚本返回非零值,git终止提交。
说明一点,这个脚本看上去和commit-msg
作用几乎一样。
也就是说,该脚本会调用commit-msg并执行。实际上,这一切都是可修改的。
pre-applypatch
会在补丁应用后但尚未提交前运行。这个脚本没有参数,可以用于对应用补丁后的工作区进行测试,或对git tree进行检查。如果不能通过测试或检查,脚本返回非零值,git终止提交。 同样需要注意,git提供的此默认脚本中只是简单调用了pre-commit,因此在实际工作中需要视情况修改。
post-applypatch
脚本会在补丁应用并提交之后运行,它不包含参数,也不会影响git am的运行结果。该脚本可以用来向工作组成员或补丁作者发送通知。

  • 其他Hooks
    pre-rebase

由git rebase
命令调用,运行在rebase执行之前,可以用来阻止任何已发发生过的提交参与变基(字面意思,找不到合适的词汇了)。默认的pre-rebase
确实是这么做的,不过脚本中的next
是根据Git项目自身而写的分支名,在使用过程中应该将其改成自己的稳定分支名称。
post-checkout
由git checkout
命令调用,在完成工作区更新之后执行。该脚本由三个参数:之前HEAD指向的引用,新的HEAD指向的引用,一个用于标识此次检出是否是分支检出的值(0表示文件检出,1表示分支检出)。
也可以被git clone触发调用,除非在克隆时使用参数--no-checkout。在由clone调用执行时,三个参数分别为null, 1, 1。
这个脚本可以用于为自己的项目设置合适的工作区,比如自动生成文档、移动一些大型二进制文件等,也可以用于检查版本库的有效性。
post-merge

由git merge
调用,在merge成功后执行。该脚本有一个参数,标识合并是否为压缩合并。该脚本可以用于对一些Git无法记录的数据的恢复,比如文件权限、属主、ACL等。
Server Side
除了本地执行的Hooks脚本之外,还有一些放在Git Server上的Hooks脚本,作为管理员,可以利用这些服务端的脚本来强制确保项目的任何规范。这些运行在服务端的脚本,会在push命令发生的前后执行。pre系列的脚本可以在任何时候返回非零值来终止某次push,并向push方返回一个错误

参考链接http://page.renren.com/601846477/channel-noteshow-918871212

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 214,951评论 6 497
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,606评论 3 389
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 160,601评论 0 350
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,478评论 1 288
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,565评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,587评论 1 293
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,590评论 3 414
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,337评论 0 270
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,785评论 1 307
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,096评论 2 330
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,273评论 1 344
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,935评论 5 339
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,578评论 3 322
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,199评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,440评论 1 268
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,163评论 2 366
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,133评论 2 352

推荐阅读更多精彩内容