Files
Garry Tanandcapy-ai[bot] a1487458d3 v1.91.241.0 fix(deps): bump dompurify, MCP SDK, zod, body-parser, fast-uri, ip-address to OSV-fixed releases (#3462) (#3463)
* fix(deps): bump dompurify, @modelcontextprotocol/sdk, zod, body-parser, fast-uri and ip-address to their OSV-fixed releases (#3462)

Co-authored-by: capy-ai[bot] <230910855+capy-ai[bot]@users.noreply.github.com>

* build(diagram-render): empty excalidraw's public Firebase config literal in the bundle; declare BUILD_INFO.json's test lane

Co-authored-by: capy-ai[bot] <230910855+capy-ai[bot]@users.noreply.github.com>

* test(diagram-render): name the bundle, BUILD_INFO and build script by repo path so the pre-gate sees their lane

Co-authored-by: capy-ai[bot] <230910855+capy-ai[bot]@users.noreply.github.com>

* chore(pregate): drop the BUILD_INFO.json lane declaration; the drift test names the file now

Co-authored-by: capy-ai[bot] <230910855+capy-ai[bot]@users.noreply.github.com>

* fix: pre-landing review fixes

Testing specialist: the drift test asserts the bundled DOMPurify is the override and the bundle carries no Google API key; deps-smoke refuses ip-address below 10.7.4 and checks every bumped package against its OSV-fixed floor in both lockfiles. Adversarial: build.ts fails when any AIza key survives the strip. Outside voice and red team: the CHANGELOG hash and scope lines match the shipped tree.

Co-authored-by: capy-ai[bot] <230910855+capy-ai[bot]@users.noreply.github.com>

* docs(diagram-render): document the Firebase-literal strip and the new drift checks

Co-authored-by: capy-ai[bot] <230910855+capy-ai[bot]@users.noreply.github.com>

---------

Co-authored-by: capy-ai[bot] <230910855+capy-ai[bot]@users.noreply.github.com>
2026-10-26 10:44:36 +00:00
..

diagram-render

Offline diagram rendering for make-pdf and /diagram. One self-contained HTML page (dist/diagram-render.html, ~9MB) bundles mermaid, the excalidraw export utilities, and the official mermaid→excalidraw converter. Callers open it through lib/aside-render.ts (the TypeScript API make-pdf embeds) or bin/gstack-render.ts (the CLI the /diagram skill runs) — in the Aside browser when it is running, otherwise in gstack's own headless browser (the browse daemon; ENGINE= on the CLI's first line says which). Either way the page's directory is served on 127.0.0.1 for one render, --eval calls the page API, and --out copies each result out (strings verbatim, data URLs as bytes).

The built page is committed (eng-review D2): rendering works with zero network at install time and render time, and there is no npm supply-chain surface in ./setup. The drift test (test/diagram-render-drift.test.ts) fails CI if dist/ is edited by hand or falls out of sync with BUILD_INFO.json. It also checks that the bundled DOMPurify is the package.json override and that the bundle carries no Google API key.

Page API (window functions)

Function In → Out
__renderMermaid(id, text) mermaid text → SVG string. id must be unique per fence (mermaid-fence-<n>) — it namespaces every internal SVG id.
__mermaidToExcalidraw(text) mermaid text → .excalidraw scene JSON (flowcharts and sequence diagrams as editable elements; other types fall back to one image element and log Error processing Mermaid diagram to the console).
__excalidrawToSvg(sceneJson) scene JSON → SVG string (Excalifont embedded, offline).
__rasterize(svg, targetWidthPx) SVG → PNG data URL. Callers own DPI math: targetWidthPx = placed width (in) × 300. Throws on tainted canvas.
__downscaleRaster(dataUri, targetWidthPx, mime) raster data URI → smaller data URI at targetWidthPx (same mime). make-pdf uses it to normalize oversized photos to print resolution.
__mountForScreenshot(svg, px) taint-proof fallback: mounts SVG at #raster-stage for gstack-render --screenshot out.png --selector '#raster-stage'.
__probeImage(src) data URI/URL → {width, height} JSON.
__bundleInfo { name, deps } — pinned dependency versions baked at build.

Readiness: poll until #status text is ready (or gstack-render ... --wait-selector '#done'). Page errors accumulate in window.__errors.

Updating

# 1. edit the exact pin in package.json
cd lib/diagram-render && bun install
# 2. rebuild (deterministic; build twice → same sha)
bun run build
# 3. commit package.json + bun.lock + dist/ together

scripts/build.ts empties the one VITE_APP_FIREBASE_CONFIG literal in @excalidraw/excalidraw's npm bundle (a public Firebase client key the offline page never uses), because a key-shaped literal fails the pre-gate secret scan. The build fails if that literal is not matched exactly once or an AIza… key survives, so an excalidraw bump that changes its shape needs the strip rule updated.

Render contract details (securityLevel strict, htmlLabels false, print-css font lock, <base href> + </scri escaping) are documented in src/entry.ts and scripts/build.ts — read both before touching either.