#!/bin/bash # # Copyright (c) 2010, Benjamin C. Meyer # All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions are met: # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in the # documentation and/or other materials provided with the distribution. # 3. All advertising materials mentioning features or use of this software # must display the following acknowledgement: # This product includes software developed by Benjamin C. Meyer. # 4. Neither the name of the project nor the # names of its contributors may be used to endorse or promote products # derived from this software without specific prior written permission. # # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER ''AS IS'' AND ANY # EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED # WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE # DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY # DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES # (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND # ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS # SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. # GHD=`dirname \`which git-hooks\`` function hook_dirs { hook="${1}" echo "${HOME}/.git_hooks/${hook}" echo "${PWD}/git_hooks/${hook}" echo "`git config hooks.global`"/${hook} } function list_hooks_in_dir { find "${1}" -executable -type f 2>/dev/null | grep -v "^.$" | sort -V } function run_hooks { dir="${1}" shift 1 for hook in `list_hooks_in_dir "${dir}"` do if [ ! -z ${GIT_HOOKS_VERBOSE} ] ; then echo -n "@@ Running hook: " echo -n `basename \`dirname "${hook}"\`` echo "/`basename "${hook}"`" fi ${hook} "$@" done } function run_hook { set -e hook=`basename "${1}"` shift 1 for dir in `hook_dirs "${hook}"`; do if [ ! -d "${dir}" ] ; then continue fi run_hooks "${dir}" "$@" done set +e } function install_hooks { if [ ! -d ".git" ] ; then echo "$1 must be run in the same directory as .git/" return 1 fi cd .git/ if [ "${1}" = "--install" ] ; then mv hooks hooks.old mkdir hooks cd hooks for file in applypatch-msg commit-msg post-applypatch post-checkout post-commit post-merge post-receive pre-applypatch pre-auto-gc pre-commit prepare-commit-msg pre-rebase pre-receive update do echo '#!/bin/bash git-hooks run "$0" "$@"' > "${file}" chmod +x "${file}" done else if [ ! -d hooks.old ] ; then echo "Error, hooks.old doesn't exists, aborting uninstall to not destroy something" return 1 fi rm -rf hooks mv hooks.old hooks fi } function list_hooks { while [ ! -d ".git" ] ; do cd .. done cat .git/hooks/pre-commit | grep 'git-hooks' > /dev/null 2> /dev/null if [ $? = 0 ] ; then echo -n "Git hooks ARE installed in this project." else echo -n "Git hooks are NOT installed." fi echo ' Listing User, Project, and Global hooks:' echo '---' for dir in `hook_dirs`; do echo "${dir}:" for hook in `list_hooks_in_dir "${dir}"` ; do echo -n `basename \`dirname "${hook}"\`` echo -e "/`basename "${hook}"` \t- `${hook} --about`" done echo "" done } case $1 in run ) if [ ! -z "${GIT_DIR}" ] ; then unset GIT_DIR fi shift run_hook "$@" ;; --install|--uninstall ) install_hooks "$1" ;; -h|--help ) echo "Git Hooks" echo "" echo "Options:" echo " --install Show all achievements." echo " --uninstall Publish existing achievements and push to origin." echo " run [cmd] Run the hooks for cmd such as pre-commit" echo " (no arguments) Show current hooks" ;; * ) list_hooks ;; esac