If you want to start some daemon in the background you can install daemontools and user supervise, but i like to use screen to start daemons in the background, so that i can easily see the output.
# check screen
if ! /usr/bin/screen -ls | awk '{print $1}' | grep "\.${SCREEN_NAME}$" >/dev/null; then
echo "starting $SCREEN_NAME"
screen -S "${SCREEN_NAME}" -d -m "$COMMAND_SCRIPT"
fi
I use this snippet, to check of a screen with a given name exists and if not start it up, i run a script i call screen-ls.sh from cron every few minutes or every minute to check is the screen is still up and running
#!/bin/bash
# this is a bigger example.
export PATH="/usr/local/bin:/bin:/usr/bin:/usr/local/sbin:/usr/sbin:/sbin"
# get seconds from input like
# 1w = 604800 or
# 2h = 7200
function get_seconds_from_input
(
TS="$1"
i="$((${#TS}-1))"
TS_LAST="${TS:$i:1}"
TS_BEFORE="${TS:0:$i}"
MAX_SECONDS="0"
case "$TS_LAST" in
"m"|"M")
MAX_SECONDS=$((TS_BEFORE*60))
;;
"h"|"H")
MAX_SECONDS=$((TS_BEFORE*3600))
;;
"d"|"D")
MAX_SECONDS=$((TS_BEFORE*86400))
;;
"w"|"W")
MAX_SECONDS=$((TS_BEFORE*604800))
;;
*)
MAX_SECONDS=$TS
;;
esac
if [ -n "$MAX_SECONDS" ] && [ "$MAX_SECONDS" -eq "$MAX_SECONDS" ] 2>/dev/null; then
if [ $MAX_SECONDS -gt 0 ]; then
echo $MAX_SECONDS
return
fi
fi
return
)
export UPTIME="$(cat /proc/uptime | cut -d ' ' -f 1 | cut -d '.' -f 1)"
# functie voor screen
function check_screen
(
export SCREEN_NAME="$1"
export COMMAND_SCRIPT="$2"
export COMMAND_UPTIME="$3"
if test -n "$COMMAND_UPTIME"; then
export MINIMAL_UPTIME="$(get_seconds_from_input "$COMMAND_UPTIME")"
if test -z "$MINIMAL_UPTIME"; then
echo "error: $SCREEN_NAME uptime $COMMAND_UPTIME, not valid, skipping"
return
fi
if test $UPTIME -le $MINIMAL_UPTIME; then
echo "skipping $SCREEN_NAME: uptime is $UPTIME, waiting until $MINIMAL_UPTIME ($COMMAND_UPTIME)"
return
fi
fi
# check screen
if ! /usr/bin/screen -ls | awk '{print $1}' | grep "\.${SCREEN_NAME}$" >/dev/null; then
echo "starting $SCREEN_NAME"
screen -S "${SCREEN_NAME}" -d -m "$COMMAND_SCRIPT"
fi
)
# functie voor screen time runs
function check_screen_runs_once_every_x
(
if test "$1" = "--exclusive"; then
export SCREEN_EXCLUSIVE="$2"
shift
shift
if screen -ls | grep -v "There is a screen" | grep -v "Socket in" | grep -v "No Sockets found" | awk '{print $1}' | cut -d '.' -f 2- | grep -q -F -x -f <(echo "$SCREEN_EXCLUSIVE" | tr "," "\n"); then
echo "skipping $1: not starting, still exclusive in use: $SCREEN_EXCLUSIVE"
return
fi
fi
export SCREEN_NAME="$1"
export EVERY_X_TIME="$(get_seconds_from_input "$2")"
export COMMAND_SCRIPT="$3"
export COMMAND_UPTIME="$4"
if test -n "$COMMAND_UPTIME"; then
export MINIMAL_UPTIME="$(get_seconds_from_input "$COMMAND_UPTIME")"
if test -z "$MINIMAL_UPTIME"; then
echo "error: $SCREEN_NAME uptime $COMMAND_UPTIME, not valid, skipping"
return
fi
if test $UPTIME -le $MINIMAL_UPTIME; then
echo "skipping $SCREEN_NAME: uptime is $UPTIME, waiting until $MINIMAL_UPTIME ($COMMAND_UPTIME)"
return
fi
fi
if test -z "$EVERY_X_TIME"; then
echo "FAILED: $*" >&2
return
fi
TIMEDIR="$HOME/.screen-ls.lastrun"
test -d "$TIMEDIR" || mkdir "$TIMEDIR"
export TIMEFILE="${TIMEDIR}/${SCREEN_NAME}.lastrun"
if test -f "$TIMEFILE"; then
cur_epoch="$(date +%s)"
stat_file="$(stat -c "%Z" "$TIMEFILE")"
diff_time="$((cur_epoch - stat_file))"
if test $diff_time -lt $EVERY_X_TIME; then
echo "$SCREEN_NAME: not starting, $diff_time < $EVERY_X_TIME"
return
fi
fi
# screen screen
if ! /usr/bin/screen -ls | awk '{print $1}' | grep "\.${SCREEN_NAME}$" >/dev/null; then
echo "starting $SCREEN_NAME (once every $2)"
screen -S "${SCREEN_NAME}" -d -m "$COMMAND_SCRIPT"
touch "$TIMEFILE"
fi
)
/usr/bin/screen -wipe >/dev/null 2>&1
screen -ls | grep -f <(screen -ls | cut -d '.' -f 2| grep "Detached" | awk '{print $1}' | sort | uniq -c | awk '$1!="1"{print "\\." $2 "[[:space:]]"}') | grep Detached | cut -d '.' -f 1 | xargs -r -t kill
# this will start_daemon.sh, but only if the system has been up for minimal 90 seconds
# if the start_daemon.sh script failed directly the screen is only restarted every 5 minute
check_screen_runs_once_every_x my_name 5m /root/bin/start_daemon.sh 90
check_screen my_name2 /root/bin/start_daemon.sh
export -f get_seconds_from_input
export -f check_screen
export -f check_screen_runs_once_every_x
# starting screens from /root/.screen-ls.d
for f in /root/.screen-ls.d/*.screen; do source "$f"; done
# for easy adding extra jobs just add them to /root/.screen-ls.d
I work a lot with puppet for my work and i liked that a lot better for system configurations than something like ansible. But because i do want to know how it works i do my home configuration with ansible.
I have created a ansible role, that you can use to create a screen-ls.sh and the cron. You can find it on my github
You can use it like this
- name: create screenls
include_role:
name: foxhunt72_screen_ls
vars:
screen_username: root
screen_filename: /root/screen-ls.sh
screen_cron_minute: "*/3"
screen_uptime_min: 10
screen_program:
- name: start_daemon
script: /root/start_daemon.sh