git hookでできること の続き
init.templatedir
gitのhooksは各プロジェクトの.git/hooks/
にあります
その元となるファイルはgitのインストール環境により違いますが
$PREFIX/share/git-core/templates/hooks/
などにあります
$ which git
/usr/local/bin/git
$ ls /usr/local/share/git-core/templates/hooks/
applypatch-msg.sample post-receive.sample pre-commit.sample update.sample
...
share/git-core/templates/hooks/
内に自分用のhookを作成しても問題ないですが、ユーザーとしてhooksのテンプレートを管理したい場合は以下のようにします。
~/.git_template/hooks
に配置します
$ mkdir -p ~/.git_template/hooks
($ cp /usr/local/share/git-core/templates/hooks/* ~/.git_template/hooks)
# 自作hookを配置
$ cp pre-commit ~/.git_template/hooks/
# 権限
$ chmod 755 ~/.git_template/hooks/pre-commit
# git configの設定
$ git config --global init.templatedir '~/.git_template'
最後のinit.templatedir
が最も重要です。(.gitconfig
に追加されます)
新規のプロジェクトでgit init
やgit clone
した場合は、そのタイミングで.git_template/hooks
をもとに.git/hooks/
が作成されるので問題ありません。
既存のプロジェクトの場合は.git_template/hooks
の内容をそれぞれ反映させる必要があります。
再度git init
を実行するとhooksが再インストールされます。ただし、すでに同ファイル名のものが存在する場合は上書きはされないようなので、
$ rm .git/hooks/pre-commit
$ git init
Reinitialized existing Git repository in /path/to/rails_project/.git/
# または上書きcp
のようにして、自分の追加したいものを反映します。
一括でたくさんの既存プロジェクトにhooksを反映
既存のプロジェクトがたくさんある場合は、追加したいhookをすべてに反映するのがかなり面倒です。
スクリプトやxargsなどを使って各プロジェクトへcopyします。
# 反映したいプロジェクトがある場所に移動
$ cd my_projects
# .gitを一覧確認
$ ruby -e 'Dir::glob("./**/.git").each{|f| puts f }'
./project1/.git
./project2/.git
...
# フックを各.git/hooksへコピー
$ ruby -e 'Dir::glob("./**/.git").each{|f| `cp ~/.git_template/hooks/pre-commit "#{f}/hooks/"` }'
# 再度確認
$ ruby -e 'Dir::glob("./**/.git").each{|f| puts `ls "#{f}/hooks/pre-commit"` }'
参考:
StackOverflow(Git commit hooks - global settings)
Global git hook -> Globalなhookは定義できず、プロジェクトごとhooksを持つ必要があるらしい