#!/usr/bin/env bash ########################################################################### ## Copyright (C) Wizardry and Steamworks 2025 - License: MIT ## ########################################################################### #set -x # check for Docker socket [ ! -S /run/docker.sock ] && \ echo "Docker socket file not found!" && \ exit 1 [ -z "${POINTER_ADDRESS}" ] && \ echo "The POINTER_ADDRESS environment variable has to be set to point to the traefik IP address." && \ exit 1 # this must be set by the container [ -z "${MDNS_DOMAIN}" ] && MDNS_DOMAIN='local' # start dbus and wait for socket dbus-uuidgen > /var/lib/dbus/machine-id mkdir -p /run/dbus PROCESS_OUTPUT=$(mktemp "${TMPDIR:-/tmp/}$(basename $0).XXX") dbus-daemon --config-file=/usr/share/dbus-1/system.conf --print-address --nofork &> ${PROCESS_OUTPUT} & PROCESS_PID=$! echo -n "waiting for dbus socket: " until grep -q -i 'unix:path' ${PROCESS_OUTPUT} do if ! ps ${PROCESS_PID} > /dev/null then echo "The process died" >&2 exit 1 fi echo -n "." sleep 1 done echo echo "dbus is running!" sleep 1 # start Avahi mDNS Daemon in the background echo "starting avahi daemon..." avahi-daemon & # create associative array to store publisher PIDs declare -A PUBLISHERS # publishers lock file LOCK_FILE='/tmp/publishers' function lock() { # acquire lock if mkdir "${LOCK_FILE}" &>/dev/null; then trap '{ rm -rf ${LOCK_FILE}; }' HUP INT QUIT TERM EXIT else exit 0 fi } function unlock() { rm -rf ${LOCK_FILE} } # trap HUP and flush function flush_mdns() { echo "got HUP signal..." for KEY in "${!PUBLISHERS[@]}" do echo "terminating advertisement for ${KEY}" kill -s TERM "${PUBLISHERS[${KEY}]}" done } trap 'flush_mdns' HUP # starting initial pass and publishing containers echo "starting initial startup pass..." curl \ -s \ --unix-socket '/run/docker.sock' \ -H 'Accept: application/json' \ 'http://localhost/containers/json' | jq -r '.[].Names[0]' | sed 's/\///g' | while read -r MDNS_HOST; do echo "advertising ${MDNS_HOST}.${MDNS_DOMAIN} as ${POINTER_ADDRESS}" avahi-publish -v -a "${MDNS_HOST}.${MDNS_DOMAIN}" -R ${POINTER_ADDRESS} & lock PUBLISHERS[${MDNS_HOST}]=$! unlock done # read Docker socket and start or stop publishers with containers echo -n "waiting for container events: " curl \ -s \ --unix-socket '/run/docker.sock' \ -H "Accept: application/json" \ 'http://localhost/events' | while read -r EVENT; do # build name.local echo -n "." MDNS_HOST=`echo ${EVENT} | jq -r '.Actor.Attributes.name'` if [ -z ${MDNS_HOST} ]; then continue fi case `echo ${EVENT} | jq -r ".status"` in "create") printf "\n" echo "advertising ${MDNS_HOST}.${MDNS_DOMAIN} as ${POINTER_ADDRESS}" avahi-publish -v -a "${MDNS_HOST}.${MDNS_DOMAIN}" -R ${POINTER_ADDRESS} & lock PUBLISHERS[${MDNS_HOST}]=$! unlock ;; "destroy") lock MDNS_PID=${PUBLISHERS[${MDNS_HOST}]} unlock printf "\n" echo "stopping advertisements for ${MDNS_HOST} running under PID ${MDNS_PID}" if [ ! -z "${MDNS_PID}" ]; then kill -s TERM "${MDNS_PID}" fi ;; esac done echo "bye!"