Gitlab 4.2 + Gitolite で Git フックを使う

Gitlab で作ったプロジェクトでフックを使おうとしたら結構苦労したのでメモ。


以下のディレクトリ構成は Gitlab のインストール手順に従った場合のものなので、Gitolite を手動インストールしたような場合は適宜読み替えを。



まず、Gitolite の機能として、/home/git/.gitolite/hooks/common 配下に入っているファイルをリポジトリ作成時に
自動的に hooks 配下へシンボリックリンクしてくれる機能があるっぽい。

そして、デフォルトでは上記の hooks/common 配下には Gitolite が update フックを、Gitlab が post-receive フックを配置している。


pre-receive フックや post-update フックが必要なのであれば普通に hooks/common へ配置するだけでいいけど、
今回はまさに update フックと post-receive フックを使いたかったので苦労したという話。



単純に考えると、既存の update フックや post-receive フックを自前のフックに置き換えてしまって、
そのフックの中から元のフックを読んでやればいいと思うだろう。

実際、post-receive についてはそれでうまくいった。*1


ところが、update フックについては、リポジトリを作るたびに Gitolite が勝手に元に(Gitolite 用のフックに)戻してしまうようだ。



で、Google 先生でいろいろ調べてみると、 update.secondary という名前でフックを作ればいいらしい*2 とのことなので、
hooks/common/update.secondary を用意してみたものの、さっぱり動かない。



なんでだろー、と公式マニュアルをよくよく見てみると、

WARNING: This is not the latest gitolite; please see the README

という警告が…。



最新のマニュアルを辿って行くと、自前の update フックを使うには、VREF(virtual refs) というものを使うことが分かった。*3

具体的にいうと、update フックとして my-own-hook を呼ばせたい場合、conf/gitolite.conf を

repo @all
    -       VREF/my-own-hook        =   @all

とすればいいらしい。


特定のリポジトリのみに指定したい場合、「repo @all」の「@all」をリポジトリ名に変えれば OK っぽいけど、
リポジトリの設定は Gitlab がガンガン書き換えるので、「repo @all」にしてフック側で $GL_REPO を見て
判断させた方がいいと思う。



というわけで、早速 git clone git@localhost:gitolite-admin して conf/gitolite.conf の変更後、git push する。

そして、自前 update フックだけれども、hooks/common 配下ではなく、VREF ディレクト*4 に置かないといけない。


フックの場所が hooks/common と VREF に別れるのが嫌だけど、そこはシンボリックリンクとかでなんとか誤魔化すということで。



ただ、ここまでやっておきながら Gitlab の v5 では Gitolite 使わなくなるらしいので、
バージョン上げた時はまた苦労するんだろうな…。

*1:Gitlab のプロジェクト一覧ページで post-receive フックが正しくないという警告が出るようになったけど

*2:こことかこことか

*3:ここの 1.3.2.2 update hook 参照

*4:gitolite query-rc GL_BINDIR で表示されるディレクトリ中の VREF ディレクトリのことらしい。自分の場合、/home/git/gitolite/src/VREF だった。