Quantcast
Channel: David Kelley » CodeDavid Kelley
Viewing all articles
Browse latest Browse all 7

Using Hooks with Git

$
0
0

Commit hooks within Git can be incredibly useful for automatically incorporating third-party tools into the pre and post commit process.

Hooks are written in shell script (BASH) and can therefore execute any program or custom tool that you need to use. Typically, these hooks are great for validating code or helping to enforce a particular coding style.

All hooks are stored in the .git/hooks folder located at the root of a repository. Git comes equipped with lots of example scripts that are already stored within this folder. Each hook receives slightly different parameters based upon the hooks intended function and the samples help with identifying them.

$ ls /path/to/my/repo/.git/hooks
applypatch-msg.sample  commit-msg.sample  post-commit.sample  post-receive.sample  post-update.sample  pre-applypatch.sample  pre-commit.sample  prepare-commit-msg.sample  pre-rebase.sample  update.sample

One problem I recently encountered was how to enforce a strict coding style for a project that 7 other developers contribute to. Lots of developers often have slightly varying styles of programming – this problem is further complicated when taking multiple languages into consideration. This project involved a substantial amount of Coffeescript; whilst this language is fairly style-restrictive, enforcing a singular style that all developers adhered to was still important. Whilst Coffeelint is still very much in its infancy, it provides enough configuration to enable a specific style to be enforced effectively.

Lets take a look at creating a pre-commit hook, which enables us to automatically validate all .coffee files within the project when any commit is attempted. First, we need to create our hook script file and ensure that it is executable.

$ touch /path/to/my/repo/.git/hooks/pre-commit
$ chmod a+x /path/to/my/repo/.git/hooks/pre-commit

Once the pre-commit file has been created, lets insert a test into the file to ensure that it is working. Open the file and insert the code below, this will make any attempt to commit files fail with the message (in red) ‘Pre-Commit Tests Failed’. Feel free to try it out for yourself at this point.

#!/bin/bash
echo -e "\e[00;31mPre-Commit Tests Failed.\e[00m"
exit 1

Exiting any hook with a non-zero value aborts the next process within the cycle.

The shell script always exits with a non-zero value causing Git to abort the pre-commit sequence. This script is less than useless at the moment, so lets insert the command and logic for (recursively) determining if all .coffee files within the project are valid and use the correct style.

#!/bin/bash

test=`find coffee/ -name "*.coffee" | xargs coffeelint -f coffeelint.json | grep Ok! | awk '{ print $1 }'`

if [ "$test" != '✓' ]; then
	find coffee/ -name "*.coffee" | xargs coffeelint -f coffeelint.json
	echo -e "\e[00;31mCoffeelint Tests Failed.\e[00m"
	exit 1
else
	echo -e "\e[00;32mCoffeelint Tests Passed.\e[00m"
fi

Whilst the above example is very specific, it is fairly simple to pipe out the determinate from the output of any process, whether that is a single character or a more complex value. This makes hooks an important asset to any project that has repetitive operations.

Hooking enables the automation of tedious tasks, and as seen in the example above, can help to enforce coding styles. Git hooks in general and their usage are further explained here.

Pro Tip: Remember to ensure that the script is executable! chmod a+x!


Viewing all articles
Browse latest Browse all 7

Trending Articles