feat: network loading spinner for pyvis graphs (shared shell)#11
Conversation
Design for a centered spinner overlay over every pyvis network output, shown during server build AND client vis-network stabilization, auto-hidden on the fork's already-emitted _stabilized signal (8s fallback). Lives entirely in the SESPy shell (dashboard.py + sespy-skin.css); no pyvis fork changes. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Task 1: shell CSS + injected JS (show on shiny:recalculating, hide on <id>_stabilized + 8s fallback) with a CLD end-state e2e. Task 2: cross-app manual smoke checklist. No pyvis fork changes. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Round-1 review (4 orthogonal agents) found: (1) BLOCKER — fork's el.innerHTML='' wipes any injected overlay; (2) MAJOR — default CLD is physics-off so _stabilized never fires; (3) MAJOR — e2e was near-vacuous; (4) MAJOR — MosaicSES serves a separate skin copy, so shared CSS wouldn't reach it. Revisions: pseudo-element spinner (survives innerHTML=''); hide on the always-sent <id>_ready (not _stabilized); sticky data-sespy-net-shown marker for a non-racy e2e; mirror the CSS into both apps' skins; bind handlers at parse time (no first-load race). Dropped the MutationObserver entirely. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Round-2 review (3 agents) confirmed the pseudo-element mechanism paints above the
canvas, _ready fires every render, and $ is available at parse (cross-app safe).
Two fixes folded in: (1) HIGH — add data-sespy-net-hidden provenance ('ready' vs
'fallback') and assert 'ready' in the e2e, so the 8s fallback can't mask a broken
_ready hide; (2) nit — rgba() background fallback before color-mix for older
engines. Confirmed SESPy + MosaicSES are the only two sespy.dashboard consumers.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Adds is-loading (+ sticky data-sespy-net-shown) on shiny:recalculating and
removes it on the fork's always-sent <id>_ready input, with an 8s fallback and
data-sespy-net-hidden provenance ('ready' vs 'fallback'). CLD e2e asserts the
show->hide cycle happened via _ready (not the fallback), non-racy. 5/5 green.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
|
Warning Review limit reached
Next review available in: 27 minutes Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available. How can I continue?After more reviews become available, a review can be triggered using the To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews. How do review limits work?CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability. For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window. Please refer docs for additional details. Review details⚙️ Run configurationConfiguration used: defaults Review profile: CHILL Plan: Pro Run ID: 📒 Files selected for processing (6)
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
What
Adds a loading spinner over every pyvis network view (Topology, CLD, Leverage, Metrics, Intervention, Loops, Simplify) in both the SESPy and MosaicSES apps, while the graph builds — auto-hidden the moment it's drawn.
How
.pyvis-network-output.is-loading::before/::after(veil + "Rendering network…" label + ring) in the shell skin. The pyvis fork runsel.innerHTML=''on every render, which would wipe an injected child — pseudo-elements and theis-loadingclass survive it.sespy/dashboard.py, injected inhead_content): addsis-loadingonshiny:recalculating, removes it on the fork's always-sent<id>_readyinput (NOT_stabilized, which never fires for the physics-off hierarchical CLD), with an 8s fallback. Stickydata-sespy-net-shown/data-sespy-net-hiddenmarkers make the behavior testable non-racily.www/sespy-skin.csscopy, so the shared JS reaches it but the CSS must be duplicated (mirror commit lives in the MosaicSES repo). z-index stays below the fork's modal (1000);pointer-events:none;rgba()fallback beforecolor-mix;prefers-reduced-motiondisables the spin.Testing
tests/test_cld_e2e.py) asserts the show→hide cycle happened via_ready(data-sespy-net-hidden == "ready"), so the 8s fallback can't mask a broken hide. 5/5 green locally.report_e2eWeasyPrint/PDF local-env issue, passes in CI's conda env).outputCoversCanvas: True).Review
Design went through two multi-agent review rounds (7 agents) — caught 1 blocker (
innerHTML=''wipe → pseudo-elements) + 4 majors (physics-off_readyhide; vacuous e2e → provenance marker; cross-app CSS). A code review of the implementation returned Ready-to-merge with only non-reachable minors. Spec + plan:docs/superpowers/{specs,plans}/2026-07-02-network-loading-spinner*.md.Companion change
MosaicSES CSS mirror: razinkele/MosaicSES (separate PR).
🤖 Generated with Claude Code