diff --git a/rc.d/rc.template b/rc.d/rc.template new file mode 100755 index 0000000..1454934 --- /dev/null +++ b/rc.d/rc.template @@ -0,0 +1,120 @@ +#!/bin/bash +# Version: 0.3.0 +# Copyright (c) 2005-2022: +# Darren 'Tadgy' Austin +# Licensed under the terms of the GNU General Public License version 3. + +EXEC="" +ARGS=() +PIDFILE="" + +# Allow configuration in /etc/default to override. +# Additional available variables: +# ENVIRONMENT=() # Extra environment passed to $EXEC. Must be an array. +# EXTRA_ARGS=() # Extra arguments passed to $EXEC. Must be an array. +# SLAY_DELAY="" # Delay between the SIGTERM and SIGKILL on a 'stop'. Default: 2s. +# RESTART_DELAY="" # Delay between stopping and starting on a 'restart'. Default: 2s. +[[ -e "/etc/default/${0##*rc.}" ]] && source "/etc/default/${0##*rc.}" + +error() { + printf "%s: %s: %s\\n" "${BASH_SOURCE##*/}" "${EXEC##*/}" "$*" >&2 +} + +checkconfigured() { + # This function can be used to perform any pre-start tests; hopfully to insure the daemon + # can start correctly, before actually trying to start it. A return value of 0 means the + # tests were passed and the daemon should be started. Any other value prevents the + # daemon from being started, and an error message will be emitted. + return 0 +} + +checkstatus() { + local RUNPIDS="$({ pgrep -f "$EXEC"; pgrep -F "$PIDFILE" 2>/dev/null; } | sort -u )" + if [[ ! -z "$RUNPIDS" ]]; then + printf "%s: %s: %s" "${BASH_SOURCE##*/}" "${EXEC##*/}" "running" + if [[ ! -z "$PIDFILE" ]]; then + if [[ ! -e "$PIDFILE" ]]; then + printf "%s" ", but .pid file does not exist" + elif ! grep "\<$(< "$PIDFILE")\>" <<<"$RUNPIDS" >/dev/null 2>&1; then + printf "%s" ", but .pid file is stale" + fi + fi + printf "\\n" + else + printf "%s: %s: %s\\n" "${BASH_SOURCE##*/}" "${EXEC##*/}" "stopped" + return 1 + fi + return 0 +} + +startdaemon() { + if [[ ! -e "$EXEC" ]]; then + error "not found" + return 1 + elif [[ ! -x "$EXEC" ]]; then + error "not executable" + return 1 + elif ! checkconfigured; then + error "not started - pre-start checks failed" + return 1 + fi + ${ENVIRONMENT:+declare ${ENVIRONMENT[*]};} "$EXEC" ${ARGS[*]} ${EXTRA_ARGS[*]} + if (( $? != 0 )); then + error "error starting daemon" + return 1 + else + return 0 + fi +} + +stopdaemon() { + [[ -e "$PIDFILE" ]] && kill -TERM "$(< "$PIDFILE")" >/dev/null 2>&1 || kill -TERM "$(pgrep -f "$EXEC" | tr $'\n' " ")" >/dev/null 2>&1 + sleep "${SLAY_DELAY:-2}" + if checkstatus >/dev/null; then + error "failed to stop gracefully - slaying" + kill -KILL "$({ cat "$PIDFILE"; pgrep -f "$EXEC"; } 2>/dev/null | sort -u | tr $'\n' " ")" >/dev/null 2>&1 + fi + return 0 +} + +case "$1" in + 'start') + if checkstatus >/dev/null; then + error "already running" + printf " %s\\n" "Try: $BASH_SOURCE status" >&2 + RET=1 + else + startdaemon + RET=$? + fi + ;; + 'stop') + if ! checkstatus >/dev/null; then + error "not running" + printf " %s\\n" "Try: $BASH_SOURCE status" >&2 + RET=1 + else + stopdaemon + RET=$? + fi + ;; + 'restart') + if checkstatus >/dev/null; then + stopdaemon && sleep "${RESTART_DELAY:-2}" && startdaemon + RET=$? + else + startdaemon + RET=$? + fi + ;; + 'status') + checkstatus + RET=$? + ;; + *) + printf "%s\\n" "Usage: $BASH_SOURCE " >&2 + RET=1 + ;; +esac + +return $RET 2>/dev/null || exit $RET