Emit embeddable chart and graph fragments for hosting in external pages #150
Reference in New Issue
Block a user
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Context
A LAN documentation server (planned, separate repo) will publish aura's design
docs and embed aura's own charts and graphs inline — using the same render engine
as the CLI, so a strategy graph or an equity curve in the docs is byte-for-byte
what
aura graph/aura chartproduce, with no second render stack to drift.That single-source goal requires aura-cli to expose its rendered output in an
embeddable form. Today it can emit only whole, self-contained pages.
Current behaviour (verified)
render_htmlandrender_chart_html(crates/aura-cli/src/render.rs) eachassemble a complete
<!doctype html>document;aura graphandaura chart <name>print it to stdout (pinned bygraph_emits_self_contained_html_viewerandchart_emits_self_contained_html_for_a_persisted_runincrates/aura-cli/tests/cli_run.rs). Four properties of that output blockembedding:
<!doctype html>…</html>document(
render.rs:98-115,:207-236) — cannot be placed inside a doc page's<body>.window.AURA_MODEL(render.rs:109)and
window.AURA_TRACES(render.rs:230). Two graphs or two charts on one pageoverwrite each other.
(
render.rs:75-81,:103-113,:223-234), including the ~1.4 MB Graphviz-WASMblob (
assets/viz-standalone.js). N embedded elements ⇒ N copies.SHELL_HEADsetshtml, body { … background: #16161a; … }(
render.rs:24). Embedded as-is, it restyles the entire host page.What an embedding consumer needs
a container element + its instance-local data + the init call. No
<!doctype>/<head>/<body>; page chrome (theaura graph/aura chartheader, breadcrumb, x-mode toggle) optional, not forced.
one page. Data is bound to a unique mount id, not to
window; each viewerinitializes against its own container.
pan-zoom, the two viewer JS, theme CSS) are loadable once per page as an
addressable, versioned/hashable bundle, separate from the fragments; fragments
assume the globals are already present.
processed data, not the raw trace files: for charts the union-spine-aligned +
decimated
ChartData(xs/series/meta + mode); for graphs the DOT (or model JSON)the viewer consumes. The alignment + decimation logic (
build_chart_data,decimateincrates/aura-cli/src/main.rs) stays aura-internal and must not bere-implemented downstream.
never global
html/bodyrules.a documented, versioned contract between the two repos; same run/blueprint + same
aura commit ⇒ byte-identical output (so a downstream mtime cache stays valid).
aura's C1 determinism already supplies this; the contract inherits it.
Open design questions (for brainstorm)
(
<div>+<script>), or aura emits only serve-ready data (ChartDataJSON /DOT) and the consumer owns the fragment template plus the shared viewer assets.
The latter matches aura's stated role — "aura is a serializer, Graphviz does the
rest" (
render.rs:1-7;docs/design/prototypes/graph-render/README.md) — butpresupposes the viewer/asset layer is shareable across repos.
(
aura chart <name>); the graph path renders only the built-in sample(
aura graph). Addressing a consumer's own blueprint is the separate concernalready filed as #28, a prerequisite for embedding arbitrary graphs (the chart
path has no equivalent gap).
Already in place (bounds the lift)
runs/traces/<name>/are already a documented,downstream-consumable columnar-SoA contract:
<tap>.jsoncarriestap/kinds/ts/columns,index.jsoncarries theRunManifest+ orderedtap list (pinned by
run_trace_persists_columnar_soa_shape_on_diskandrun_trace_index_carries_manifest_and_ordered_tap_list,crates/aura-cli/tests/cli_run.rs).buildChartsinassets/chart-viewer.jsis pure (no DOM, no uPlot); the vendored assets live incrates/aura-cli/assets/.References
prerequisite for arbitrary embedded graphs)
same render output)
ChartDataof R4carries the decimated series)
Re-anchoring after cycle #295 (aura-runner/aura-measurement extraction) and the #28 closure — the R1-R6 ask is unchanged and still unaddressed, but two references in this issue are stale and one dependency has cleared:
Line citations have drifted with unrelated edits, not with any fix to the properties they describe. Current locations: render_html spans crates/aura-cli/src/render.rs:86-103 (window.AURA_MODEL injected at line 97); render_chart_html spans crates/aura-cli/src/render.rs:195-221 (window.AURA_TRACES injected at line 218). All four blocking properties (whole-page document, global window singletons, per-call asset inlining, global CSS) remain verified true at these locations.
The 'html, body { background: #16161a; … }' citation at render.rs:24 is stale: SHELL_HEAD (crates/aura-cli/src/render.rs:18-30) now splices its style body from crates/aura-cli/assets/aura.css via include_str! (the #209 single-source-CSS convention). The actual global rule is crates/aura-cli/assets/aura.css:31 (
html, body { … background: var(--bg); … }). R5's scoped-styling ask should cite aura.css going forward, not render.rs.#28, listed here as an open coupled prerequisite ('graph source addressing... the separate concern already filed as #28'), closed 2026-07-10.
aura graph <blueprint.json>now renders an arbitrary consumer blueprint (crates/aura-cli/src/main.rs:1859dispatch_graph, viais_blueprint_fileat :1421) — the built-in-sample-only limitation this issue's design-questions section flagged as blocking arbitrary embedded graphs no longer exists. #150's graph path and chart path are now on equal footing; nothing here needs to wait on #28 anymore.On the open design question ('where the assembly lives'): #28's closing decision (2026-07-10) explicitly dropped a downstream-linkable Rust render crate in favor of keeping the consumer surface CLI-over-blueprint-data ('the ratified consumer surface is CLI-over-blueprint-data… not by linking a Rust render library'). That is a direct precedent for this issue's first open question and leans toward 'aura emits fragments/data via CLI output' over 'consumer links an aura render library' — worth weighing when this is picked up, though it does not by itself pick between R1's two sub-options (ready-made
<div>+<script>fragments vs raw ChartData/DOT data for the consumer to template).Separately, cycle #295 (crates/aura-runner, crates/aura-measurement) established the project's current pattern for CLI-embedded logic a downstream consumer needs: extract it into a library crate reachable without the binary. R4's
build_chart_data/decimate(crates/aura-cli/src/main.rs:147, :230) remain private fns inside the CLI binary and were not touched by that extraction — they are a candidate for the same C28-style move if/when this issue is implemented, though that is this issue's call to make, not a prerequisite blocking it.No change to the R1-R6 requirements or the #72/#110/#112 references; both remain applicable as written.