apply/run
2021-07-15 22:43:02 -04:00

168 lines
3.2 KiB
Bash
Executable file

#!/bin/sh
set -e
set -u
RED="$(printf "\033[31m")" # "$(tput setaf 1)"
GREEN="$(printf "\033[32m")" # "$(tput setaf 2)"
YELLOW="$(printf "\033[33m")" # "$(tput setaf 3)"
BLUE="$(printf "\033[34m")" # "$(tput setaf 4)"
RESET="$(printf "\033(B\033[m")" # "$(tput sgr0)"
usage() {
echo "usage: $(basename "$0") [-v] <target> [<target>...]"
exit 1
}
root_path() {
if [ -z "${APPLY_ROOT:-}" ]; then
cd -- "$(dirname "$0")" >/dev/null 2>&1 && pwd
else
echo "$APPLY_ROOT"
fi
}
read_group() {
local target="$*"
while read -r item; do
# Ignore comments
case "$item" in
'#'*)
;;
*)
echo "$item"
;;
esac
done < "$(root_path)/$target"
}
run_group() {
local target="$*"
for item in $(read_group "$target"); do
# Ignore comments
case "$item" in
'#'*)
;;
*)
run_pretty "$item"
;;
esac
done
}
run_unit() {
/bin/sh -l -c "set -e; set -u; set -o pipefail; . ./lib; test -f facts && . ./facts; . '$(root_path)/$*'"
}
log_file() {
echo -n "$LOG_DIR/"
echo -n "$(echo "$1" | sed 's/\//_/g')"
echo ".log"
}
check_target() {
local target="$*"
if [ ! -f "$(root_path)/$target" ]; then
echo "missing $target"
return 1
fi
case "$target" in
groups/*)
for item in $(read_group "$target"); do
check_target "$item"
done
;;
esac
}
run_pretty() {
local target="$*"
case "$target" in
groups/*)
printf "${YELLOW}** ${BLUE}%s ${YELLOW}processing...${RESET}\n" "$target"
run_group "$target"
printf "${YELLOW}** ${BLUE}%s ${GREEN}OK${RESET}\n" "$target"
;;
units/*)
run_pretty_unit "$target"
;;
*)
echo "unsupported command: $target"
;;
esac
}
run_pretty_unit() {
local rc
local log_file
local target="$*"
printf "${YELLOW}** ${BLUE}%s${RESET}" "$target"
[ "$VERBOSE" = "1" ] && echo ": ${YELLOW}starting...${RESET}"
log_file=$(log_file "$@")
if [ "$VERBOSE" = "1" ]; then
set +e
run_unit "$@"
rc=$?
set -e
else
set +e
run_unit "$@" >"$log_file" 2>&1
rc=$?
set -e
fi
if [ "$VERBOSE" = "1" ]; then
printf "${YELLOW}** ${BLUE}%s${RESET}: " "$target"
else
printf " "
fi
if [ $rc -eq 0 ]; then
echo "${GREEN}OK${RESET}"
else
echo "${RED}FAILED${RESET}"
if [ "$VERBOSE" = "1" ]; then
echo "For details, see output above" 1>&2
else
echo "Here are the last lines of output:" 1>&2
tail -n20 "$log_file" 1>&2
echo "For details, see $log_file" 1>&2
fi
exit $rc
fi
}
if [ $# -lt 1 ]; then
usage
fi
if [ "$1" = "-v" ]; then
VERBOSE="1"
shift
else
VERBOSE="0"
fi
if [ $# -lt 1 ]; then
usage
fi
# pre-flight checks
for target in "$@"; do
check_target "$target"
done
# fly!
LOG_DIR="$(mktemp -d)"
for target in "$@"; do
run_pretty "$target"
done