#!/bin/sh -e

if test -z "$1" ; then
  echo "svctl-restart: usage: svctl-restart service..." 1>&2
  exit 100
fi

if ! test -L /run/s6-rc/compiled ; then
  echo "svctl-restart: fatal: s6-rc is not running" 1>&2
  exit 2
fi

list=$(s6-rc-db atomics "$@")

# Oneshots have to be taken down before they can run again: "s6-rc -u change" on
# an already-active oneshot is a no-op, so until 2026-09-22 "svctl restart" on a
# oneshot did nothing at all and still exited 0 -- every "notify => Service[...]"
# on a oneshot was silently lost (S6-SYSTEM.md, and the Puppet provider reported
# "Triggered 'refresh'" for it).
#
# Note what this implies: taking a oneshot down takes its dependants down too,
# and "s6-rc -u change" below brings the named service back up, not them. That is
# s6-rc's dependency semantics, and it is the reason this only happens for
# oneshots that are actually up -- restarting a stopped one would have no
# meaning either way.
downagain=""
for i in $list ; do
  t=$(s6-rc-db type "$i")
  if test x"$t" = x"longrun" ; then
    s6-svc -r "/run/s6-rc/scandir/$i"
  elif test x"$t" = x"oneshot" ; then
    if s6-rc -a list | grep -qFx "$i" ; then
      downagain="$downagain $i"
    fi
  fi
done

if test -n "$downagain" ; then
  # shellcheck disable=SC2086
  s6-rc -d change $downagain
fi

exec s6-rc -u change "$@"
