From 5c59eecff2cdf658dea7d5ea573f44cac5f4fcde Mon Sep 17 00:00:00 2001 From: Lukas Remis Date: Mon, 14 Sep 2026 20:48:29 +0200 Subject: [PATCH] Deploy: make the database wait say why it is failing MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit On a Synology first run, migrate exited with "postgres:5432 never accepted a connection" after the full 180s — and that was the entire diagnostic output, despite the network being demonstrably fine afterwards (postgres resolved and port 5432 was open from a throwaway container on the same network). The retry loop caught OSError and discarded it. It now prints the first failure immediately and repeats every 30s, with the hostname's resolved address alongside, and includes the last error in the final message. A DNS failure, a refused connection and a silently dropped packet each produce a different line instead of the same useless one. Co-Authored-By: Claude Opus 5 Claude-Session: https://claude.ai/code/session_01Nux3LCu4zP9nih4BRhPyHw --- docker/entrypoint.sh | 26 ++++++++++++++++++++++++-- 1 file changed, 24 insertions(+), 2 deletions(-) diff --git a/docker/entrypoint.sh b/docker/entrypoint.sh index f233433..d435da9 100755 --- a/docker/entrypoint.sh +++ b/docker/entrypoint.sh @@ -38,15 +38,37 @@ host = parsed.hostname or "postgres" port = parsed.port or 5432 deadline = time.time() + float(os.environ.get("DB_WAIT_SECONDS", "180")) +# Report WHY it is not connecting, not just that it isn't: the first failure +# immediately, then every 30s. A silent retry loop that ends in "never accepted" +# tells whoever is installing this precisely nothing. +last_error = None +next_report = 0.0 + while time.time() < deadline: try: with socket.create_connection((host, port), timeout=3): print(f"[entrypoint] database accepting connections at {host}:{port}") sys.exit(0) - except OSError: + except OSError as exc: + last_error = exc + if time.time() >= next_report: + try: + resolved = socket.gethostbyname(host) + except OSError as dns_exc: + resolved = f"UNRESOLVED ({dns_exc})" + print( + f"[entrypoint] waiting for {host}:{port} " + f"(resolves to {resolved}): {type(exc).__name__}: {exc}", + flush=True, + ) + next_report = time.time() + 30 time.sleep(2) -print(f"[entrypoint] ERROR: {host}:{port} never accepted a connection", file=sys.stderr) +print( + f"[entrypoint] ERROR: {host}:{port} never accepted a connection. " + f"Last error: {type(last_error).__name__}: {last_error}", + file=sys.stderr, +) sys.exit(1) PYEOF }