Live failure on otech17/cluster-bootstrap (2026-05-01): the JobDetail
flow canvas rendered as yellow horizontal lines with zero visible
bubbles. Investigation showed nodes drifted to x=30,400+ in viewBox
coordinates because the dependency graph had longest-path depth ~190
(bp-* leaves chained through "applications"). At PER_DEPTH_X=160 that
placed nodes far outside the MAX_VBOX_W=1200 ceiling. The viewBox
captured only a 1200px slice of a 30,000px cluster, so 99% of bubbles
rendered off-canvas. The few yellow lines visible were edges from the
selection job (openJobId) that happened to cross the visible window.
Pre-existing bounded tests modelled depth=0/1 stars only (#486#499) so
this pathology slipped through.
Operator's two explicit asks for this fix:
1. "No single bubble could be outside of the canvas."
2. "Max distance of a line cannot be longer than a percentage of canvas."
Implementation — Constraint A + Constraint B as a render-time projection:
* Compute the natural cluster bbox from livePos as before, clamp to
MIN/MAX viewBox.
* When natural bbox exceeds the viewBox, anchor vbX/vbY at the
left-most / top-most cluster point (instead of centring on the
cluster centroid which placed depth 0 at x=-15,000).
* Linear-scale every render position so the cluster fits inside an
inset rectangle (vbX+CLAMP_INSET .. vbX+vbW-CLAMP_INSET).
Pathological depth=190 chains compress to fit; sparse graphs with
scale=1 are unchanged.
* Hard-clamp every position into the inset rectangle as a final safety
net (FP drift, partial-tick frames). No bubble can ever sit outside.
* Edges read renderPos so they're drawn between already-clamped
endpoints — line length is bounded by the viewBox diagonal, no
"kilometers of edges" possible regardless of what the simulation
produces.
Test:
* New `keeps every bubble inside the viewBox for a deep dependency
chain` — 50-node depth chain (each at depth=i, mirroring production
shape). Asserts every centroid inside [vbX, vbX+vbW] × [vbY, vbY+vbH]
AND every line length <= viewBox diagonal. Strict — no overshoot
tolerance. Fails on main, passes after the fix.
* All 11 pre-existing bounded tests still pass; tsc clean.
Live verification + Playwright screenshot to follow on the deployed SHA.
Co-authored-by: alierenbaysal <alierenbaysal@noreply.github.com>
Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>