319

I've written a Git post-commit hook and it works correctly. However, I want to add this hook to apply to all current (and future) Git repositories I am working on. I tried adding the hook to my ~/.git/hooks/ directory instead of in the hooks directory in the project directory, however, this did not seem to work.

Is there a way to create global Git hooks that will apply to all repositories on my system (without having to copy them into each project directory)? If not, what would be the best solution going forward -- perhaps a git-init template?

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
swanson
  • 7,377
  • 4
  • 32
  • 34

4 Answers4

312

As of Git 1.7.1, you can set init.templatedir in your gitconfig to tell Git where to look for templates.

Set it like this:

git config --global init.templatedir '~/.git_template'

Afterward, new repositories you create or clone will use this directory for templates. Place the hooks you want in ~/.git_template/hooks. Existing repositories can be reinitialized with the proper templates by running git init in the same directory .git is in.

For Git versions older than 1.7.1, running git init --template ~/.git_template will work if you're like me and still want to manage your .git_template directory along with the rest of your dot files. You can also use the $GIT_TEMPLATE_DIR environment to tell git init where your template directory is.

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
sklnd
  • 4,471
  • 3
  • 21
  • 8
  • 66
    Great answer. If anybody else wonders if re-running `git init` on an existing repo wipes it - **it does not**, see: http://stackoverflow.com/questions/5149694/does-running-git-init-twice-initialize-a-repository-or-reinitialize-an-existing – kontur Oct 10 '13 at 13:16
  • For me it didn't work with the relative path to the git template folder for copying files using git init on existing repositories. I had use the full path instead. – user847988 Feb 16 '15 at 13:10
  • 2
    Just an fyi, ~/.git_template is not automatically created for you with the command. You still have to do that yourself with mkdir ~/.git_template – Geuis May 22 '15 at 01:04
  • 2
    On windows without quotation: ` git config --global init.templatedir d:\git\.git_template\ ` – Vladimir Vukanac Jul 02 '15 at 20:03
  • 2
    Tip: The template hooks are copied. If you want to be able to update the global hooks together, put the hook elsewhere and add a symbolic link in the template directory (on Linux). Make sure the link path is absolute. – Tim Allclair Jul 29 '16 at 03:52
  • There is now a way to have centralized hooks, see @VonC 's answer – Moberg Nov 11 '16 at 09:17
  • 1
    Running `git init` didn't actually update the hooks for me. It seems it will not overwrite files that are already there. [stackoverflow.com/questions/10791486/](http://stackoverflow.com/questions/10791486/how-to-replace-local-git-hooks-with-updated-versions-with-git-init). Instead you need to remove the old hook files first. – Phil R Feb 21 '17 at 22:34
  • @sklnd what about cloning an app? will it work for that or if I want to make it, what should be done? Thanks! – kamal Mar 02 '17 at 06:09
  • As its a global config, how can I revert? will delete ~/.git_template work? – kamal Mar 02 '17 at 06:16
  • isn't `--global` user-based? I need this to work with multiple users (e.x. Jenkins build on commit). How to setup with `--system`? Just modify system config file to add `init.templatedir='~/.git_template'` or it only works with global config? – Paulius Vindzigelskis Jul 17 '18 at 22:47
  • So to answer my own question (after some tests), yes - it is possible with `--system` config. Just add `sudo` in front as it is accessing system folders. If You can't use sudo, then edit or create `etc/gitconfig` file. For creating: 1st line `[init]`, 2nd line`templatedir = ~/.git_template` – Paulius Vindzigelskis Jul 17 '18 at 23:08
  • In Windows CMD, you should remove single quotes! E.g. `git config --global init.templatedir ~/.git-template`. Also, the default template folder is in: `C:\Program Files\Git\mingw64\share\git-core\templates` – Mir-Ismaili Sep 02 '22 at 19:56
  • the link is broken – DrBeco Jun 26 '23 at 01:20
285

I want to add this hook to apply to all current (and future) git repositories I am working on

With git 2.9+ (June 2016), all you would do is:

git config --global core.hooksPath /path/to/my/centralized/hooks

See "change default git hooks": this has been done to manage centralized hooks.

Community
  • 1
  • 1
VonC
  • 1,262,500
  • 529
  • 4,410
  • 5,250
  • if i have an exisiting repo and want all other dev's who pull changes to have an updated pre-commit hook for example how would i do this ? thank you – Richlewis Nov 11 '16 at 15:45
  • 2
    @Richlewis do you mean http://stackoverflow.com/a/40550555/6309 was not completely clear? – VonC Nov 11 '16 at 15:47
  • @Richlewis You would need to setup a shared folder accessible by all devs, for them to reference in their own local config. – VonC Nov 11 '16 at 15:47
  • unfortunately i still don't quite get it. within the repo there is `/.git/hooks/pre_commit` can i point it to that ? – Richlewis Nov 11 '16 at 15:49
  • @Richlewis I have answered you on your original question. – VonC Nov 11 '16 at 15:59
73

If you want them everywhere on your system (including users besides you), you can modify the contents of the installed template directory - those are in $PREFIX/share/git-core/templates/hooks, where $PREFIX is probably /usr/local or /usr.

If you want this to just be for you, then yes, the simplest thing would be the --template option of git-init. You could easily keep a personal template directory which has symlinks back to the installed version of defaults you want to keep (individual hooks, the info directory...) and then your own content in hooks/post-commit and anything else you want to customize.

Cascabel
  • 479,068
  • 72
  • 370
  • 318
  • 11
    Thanks, this worked out well. And to retroactively apply it to my existing projects, I just ran `git init` again and it added my new hook. – swanson Feb 19 '10 at 02:33
  • This is a neat workaround, but it would require that you change all your repos. This is feasable, but isn't there some possibility with a plugin or something (this is how it is done at Bazaar)? – Martin Ueding Jul 16 '11 at 04:40
  • 2
    For SourceTree's embedded git on OS X, they're in `/Applications/SourceTree.app/Contents/Resources/git_local/share/git-core/templates/hooks` – CupawnTae Sep 24 '14 at 08:31
  • 2
    For Windows this is found in the git install directory under `mingw64\share\templates\hooks` (or mingw32 for 32-bit) – nerdherd Sep 03 '15 at 17:32
  • 1
    @nerdherd it's now at `mingw64\share\git-core\templates\hooks` (gfw 2.25) – RJFalconer Feb 27 '20 at 17:28
  • Where the answer talks about `the contents of the installed template directory - those are in $PREFIX/share/git-core/templates/hooks` - would that apply to an on-prem GitHub instance, so that ALL repos in our org get the hooks? – Max Cascone Jun 09 '21 at 15:56
6

A minimalist approach is to create a git_hooks/ directory in your repository to track the hooks that you write for that project, bring it to the attention of future users by mentioning it in a README, and rely on them to do the right thing after they have cloned. I have cogitated on this for a while and chose an incremental approach. Down the road I might consider using a tool like git-hooks.

Neil Best
  • 817
  • 9
  • 17