Auto-restart the whiteboard render sidecar if it crashes
Build and push server image / test (push) Successful in 16s
Build and push server image / build-and-push (push) Successful in 1m57s

Root cause of "whiteboard stuck on old content, no errors anywhere":
the Node sidecar had crashed at some point and, since it was just a
bare backgrounded process with nothing supervising it, stayed dead
permanently. Every refresh since then hit connection-refused, which
get_or_refresh_whiteboard treats as a soft failure and falls back to
the last successfully cached image -- so it looked exactly like a
caching bug from the outside, silently, forever, with no error visible
anywhere except a crash trace that had already scrolled out of the log
buffer.

Wrap it in a restart loop instead of a bare `&` so a future crash (a
still-unknown third jsdom/Excalidraw edge case, most likely) is a
few-second hiccup instead of a silent permanent outage.
This commit is contained in:
2026-07-23 21:22:17 -04:00
parent 1100580c2c
commit 1c67dd20d7
+18 -4
View File
@@ -3,8 +3,22 @@
# sidecar, see its own README) in the background, bound to 127.0.0.1 --
# reachable from this container's Python process, never from outside it.
# Then execs uvicorn as the foreground/PID 1 process so it receives
# Docker's stop signal directly. The backgrounded Node process has no
# state worth flushing on shutdown -- fine for it to just die with the
# container.
node ./render-service/server.js &
# Docker's stop signal directly.
#
# Wrapped in a restart loop, not a bare `node ... &`: a bare background
# process that crashes stays dead for good, with nothing to bring it
# back -- turning any single render crash (a not-yet-found jsdom/
# Excalidraw edge case, say) into a silent, permanent whiteboard outage
# that looks exactly like "stuck showing stale content forever" from the
# outside, since routers/common.py's get_or_refresh_whiteboard falls
# back to the last good cached image on every failed refresh rather than
# going blank. The 2s sleep just avoids a hot-crash-loop pegging a core
# if something's wrong at every single startup.
(
while true; do
node ./render-service/server.js
echo "whiteboard render sidecar exited (code $?) -- restarting in 2s" >&2
sleep 2
done
) &
exec uvicorn app.main:app --host 0.0.0.0 --port 8420