-
Notifications
You must be signed in to change notification settings - Fork 0
/
hook-wrapper
executable file
·94 lines (85 loc) · 2.95 KB
/
hook-wrapper
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
#! /usr/bin/env sh
set -e
# Wrapper for run scripts in ${g_hooks_source}/<hook-name>.d
# Run it directly to setup
# Opts
g_hooks_source='../git-hooks' # Storage for <hook-name>.d (can be relative to this script)
g_page_size=20 # Maximum hooks per page
TAG='[HOOK-WRAPPER]' # Prefix in logs
# Find real path. Details on http://stackoverflow.com/a/29835459
rreadlink() (
target="$1" fname= targetDir= CDPATH=
{ \unalias command; \unset -f command; } >/dev/null 2>&1 || true
[ -n "${ZSH_VERSION}" ] && options[POSIX_BUILTINS]=on
while :; do
[ -L "${target}" ] || [ -e "${target}" ] || { command printf '%s\n' "ERROR: '${target}' does not exist." >&2; return 1; }
command cd "$(command dirname -- "${target}")"
fname=$(command basename -- "${target}")
[ "${fname}" = '/' ] && fname=''
if [ -L "${fname}" ]; then
target=$(command ls -l "${fname}")
target="${target#* -> }"
continue
fi
break
done
targetDir=$(command pwd -P)
if [ "${fname}" = '.' ]; then
command printf '%s\n' "${targetDir%/}"
elif [ "${fname}" = '..' ]; then
command printf '%s\n' "$(command dirname -- "${targetDir}")"
else
command printf '%s\n' "${targetDir%/}/${fname}"
fi
)
# Stolen from http://www.etalabs.net/sh_tricks.html
# escape args and print in array-like form
asave () {
for i do printf '%s\n' "${i}" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
printf '%s\n' ' '
}
# escape find results and print in array-like form
afind () {
find "$@" -exec sh -c "for i do printf %s\\\\n \"\${i}\" \\
| sed \"s/'/'\\\\\\\\''/g;1s/^/'/;\\\$s/\\\$/' \\\\\\\\/\"
done; printf '%s\n' ' '" dummy '{}' +
}
setup() {
. "$(dirname -- "${self}")/hook-setup"
}
wrapper() {
printf "\n${TAG}: %s\n" "Begin '${hook}'..."
hook_d="$(rreadlink "${g_hooks_source}/${hook}.d/")"
if [ ! -e "${hook_d}" ] || [ ! -d "${hook_d}" ]; then
printf "${TAG}: %s\n" "Missed '${hook_d}', nothing to do..."
exit 0
else
args=$(asave "${@}")
eval "set -- $(afind "${hook_d}" -maxdepth 1 -type f | sort -n | sed '/^[[:space:]]*$/d'; printf '%s\n' ' ' )"
[ "$#" -eq 0 ] && printf "${TAG}: %s\n" "Empty '$(basename -- "${hook_d}")', nothing to do..."
for file; do
if [ -s ${file} ] && [ -x ${file} ]; then
printf "${TAG}: %s\n" "Running '$(basename -- "${file}")'..." #"Args: ${*}"
(eval "set -- ${args}"; "${file}" "${@}"); err=$?
[ ${err} -ne 0 ] && printf "${TAG}: %s\n" "...Failed with '${err}'" >&2 && exit ${err}
else
printf "${TAG}: %s\n" "Empty/non-exec '$(basename -- "${file}")', ignoring..."
continue
fi
done
fi
printf "${TAG}: %s\n" "Completed '$(basename -- "$0")'."
return 0
}
# Begin
IFS="$(printf '%b' '\n\t')"
self="$(rreadlink "$0")"
hook="$(basename -- "$0")"
[ ! x"{g_hooks_source}" = x ] && [ "${g_hooks_source#/}" = "${g_hooks_source}" ] \
&& g_hooks_source="$(dirname -- "${self}")/${g_hooks_source}" \
|| g_hooks_source="$(dirname -- "${self}")/../git-hooks}"
case "${hook}" in
"$(basename -- "${self}")") setup "${@}";;
*) wrapper "${@}";;
esac
exit 0