If you have ever set RestartSec on a systemd service and wondered why you still get Address already in use errors on restart, here is why.
When RestartSec triggers a restart, systemd changes the PID but does not wait for the old process to fully release its resources. The new process starts, gets a new PID, but the old process is still holding port 443 or whatever for a few hundred milliseconds.
The fix is straightforward. Use Type=oneshot which tells systemd to treat the service as a one-shot job. It will not try to manage the process lifecycle the same way, and subsequent restarts wait for the previous invocation to fully clean up.
Or add a small delay with ExecStartPre=/bin/sleep 1. One second is usually enough.
This bit me on a reverse proxy service that kept failing to bind 443 on restarts. The logs looked clean - new PID, service started - but connections were being refused. Took a while to realize the old process was still sitting on the port.
Source: systemd.service 5 manpage - specifically the RestartSec behavior around process exit synchronization.
Top comments (0)