Add support for systemd socket activation#584
Conversation
roborev: Combined Review (
|
29b25d1 to
633fa45
Compare
roborev: Combined Review (
|
This commit facilitates running roborev as a socket-activated systemd user service. When LISTEN_FDS is set (handled by go-systemd internals), the daemon uses the systemd-provided socket instead of creating its own, enabling on-demand startup and lifecycle management driven by systemd. We enforce that socket activation is used only with loopback TCP listeners and unix sockets with safe permissions. We also avoid cleaning up the socket file in this mode, since we don't own it. Closes roborev-dev#569. Signed-off-by: Aaron Jacobs <atheriel@gmail.com>
CleanupZombieDaemons previously called KillDaemon for unresponsive zombies, which unconditionally unlinked Unix sockets. When the zombie's socket matched the systemd-managed target, this broke future connects. Now we kill the process and clean up the runtime file while preserving the socket. Also add daemon.SdNotify(READY=1) so Type=notify systemd units work correctly, and fix go-systemd dependency classification (direct, not indirect). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
When killing a zombie whose socket matches the systemd target, verify the process is actually gone before removing runtime metadata. If the kill fails, leave the runtime file so the next startup attempt can retry. Also guard against nil listener entries from activation.Listeners(), which returns nil for unsupported socket types (e.g. UDP FDs). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
killProcess returns true when the PID has been reused by a non-roborev process, since the original daemon is gone. The previous isProcessAlive check would see the reused process as alive and leave stale runtime metadata behind, blocking startup on the systemd-managed socket. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Exercises the CleanupZombieDaemons target-socket path where killProcess returns true because the PID was reused by a non-roborev process. Verifies the runtime file is removed while the socket is preserved. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Abstract sockets (@name) don't exist on the filesystem, so they can't be permission-checked or recorded in runtime metadata. Reject them early with an actionable error pointing at ListenStream= rather than letting them fall through to a confusing "path must be absolute" error from ParseEndpoint. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
roborev: Combined Review (
|
|
Addressed some minor things from running roborev reviews, will merge this soon |
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
roborev: Combined Review (
|
This commit facilitates running roborev as a socket-activated systemd user service. When
LISTEN_FDSis set (handled by go-systemd internals), the daemon uses the systemd-provided socket instead of creating its own, enabling on-demand startup and lifecycle management driven by systemd.We enforce that socket activation is used only with loopback TCP listeners and unix sockets with safe permissions.
We also avoid cleaning up the socket file in this mode, since we don't own it.
Closes #569.
Sample systemd user service and socket files, which we could put into the documentation:
These both go into
~/.config/systemd/user. To runroborevas a socket-activated user service, you'd then: