You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Add a helper pack, packs/figures/svg-figures, exposing an svg-figures skill
that authors self-contained, accessible, brand-consistent SVG figures for
research deliverables, for the figure classes Mermaid cannot express, and wires
them into the report-to-channel pipeline as first-class, MIF-citable artifacts.
Problem and motivation
The harness mandates that every figure be a fenced mermaid block: "never ASCII
art, an image link, or Graphviz/DOT", and a required figure is never silently
omitted. That rule buys determinism, provenance-friendliness and portability, and
it should stay the default. The rule is currently duplicated across many pack SKILL.md files (financial-analysis, competitive-quadrant, sustainability-report,
customer-research, market-sizing, trend-modeling and more) rather than living in
one shared contract.
The limitation is expressiveness. Mermaid covers a narrow set (flowcharts, quadrantChart, sequence, a few others). It cannot produce:
data-precise charts: grouped, stacked and 100%-stacked bars, line and area with
real axes, scatter with a trendline, dot and lollipop, small multiples;
a calibrated two-axis quadrant (today competitive-quadrant plots vendors on
a quadrantChart that cannot place points to a real scale);
timelines and Gantt with true date scales, range and dumbbell charts, simple
sankey and flow, heatmaps, KPI and stat panels;
a branded cover or hero figure, annotated schematics, or anything needing exact
layout, typography and brand color.
A genre that needs one of these has no first-class path: it bends Mermaid past its
limits, describes the figure in prose, or omits it. There is no shared figure
helper, no accessibility contract, no brand contract, and no provenance for
figures. In a MIF harness a chart asserts a claim drawn from findings, so it
should be a citable artifact that traces to its evidence, not an opaque blob.
Proposed solution
A new pack, packs/figures/svg-figures (one skill per plugin, per the harness
convention), with an svg-figures skill that, given a figure spec plus data drawn
from findings, emits a deterministic, self-contained, accessible,
brand-consistent SVG.
What it authors. The chart classes Mermaid lacks (listed above), each emitted
as a self-contained SVG: no external fetches, fonts via the system stack, a
responsive viewBox, and an accessibility contract (role="img", <title> and <desc>, an aria-label, AA contrast, and no color-only encoding, so every
series carries a pattern, shape or direct label as well as a hue).
Determinism. No Date.now or Math.random in the path. An identical spec
plus data produces byte-identical SVG, so figures diff and round-trip cleanly,
matching the harness determinism posture.
Brand. Figures use the MIF brand tokens (machine-cyan and human-amber on a
dark or light field) through the mif-brand skill. mif-brand is not currently
vendored in the template, so the pack should vendor the brand-token subset (or
declare a dependency on it) and never hard-code hex.
MIF integration (the differentiator). A figure is a MIF artifact. The skill
emits the SVG plus a sidecar (or frontmatter) recording provenance (the findings
or data rows the figure was built from), a caption, and the alt text, so a figure
is citable and its claims trace to evidence, consistent with the report channel
being the MIF Level-3 source of truth.
Channel integration and degradation. SVG inlines directly in pdf, book, blog and the reports site surface. Where a channel cannot take inline SVG (for
example notebooklm, jats, xbrl, github-issues and github-discuss), the
skill emits a deterministic raster (PNG) fallback or a Mermaid approximation, and
never silently drops a required figure (mirroring the existing rule).
Reconciling with the Mermaid-only rule. Keep Mermaid as the default for the
figures it does well (cheap, inline, no asset). Position SVG as the opt-in path for
figure classes Mermaid cannot represent. Centralize the duplicated per-pack figure
rule into one shared contract that the packs reference, and amend it to: "Mermaid
by default; when the svg-figures pack is enabled, SVG is permitted for figure
classes Mermaid cannot represent, with a raster fallback for channels that cannot
inline SVG."
Pack mechanics (fits the harness).packs/figures/svg-figures/ ships .claude-plugin/plugin.json (validated against schemas/pack.schema.json), skills/svg-figures/SKILL.md, evals/evals.json and README.md. It is toggled
through harness.config.jsonpacks[] (bash scripts/sync-packs.sh, bash scripts/pack-toggle.sh svg-figures on) and versioned with bash scripts/bump-version.sh --pack figures/svg-figures. The core hardwires no
packs, so it ships off by default.
Acceptance criteria (EARS)
WHEN a genre requests a figure class Mermaid cannot express and the svg-figures pack is enabled, the skill SHALL emit a self-contained SVG that
parses as well-formed XML and carries <title>, <desc> and an aria-label.
The skill SHALL be deterministic: GIVEN an identical figure spec and data, it
SHALL produce byte-identical SVG.
WHERE a target channel cannot inline SVG, the skill SHALL emit a deterministic
raster fallback and SHALL NOT silently omit a required figure.
The skill SHALL record figure provenance (the findings or data the figure was
built from) so the figure is a citable MIF artifact.
IF a figure would encode information by color alone, THEN the skill SHALL add a
non-color channel (pattern, shape or direct label).
The pack SHALL ship evals/evals.json, its plugin.json SHALL validate against schemas/pack.schema.json, and bash scripts/verify.sh SHALL stay green with
the pack enabled.
Alternatives considered
Extend Mermaid only. Rejected: it cannot do data-precise, branded or
annotated figures, and its theming is limited.
Allow arbitrary image links. Rejected: it breaks the determinism,
provenance and portability the harness depends on, which is the reason the
Mermaid-only rule exists.
A matplotlib or Vega renderer pack. Heavier: it pulls a Python or JS
rendering toolchain into a template that prizes stdlib and no build step, and
raster fonts and anti-aliasing are non-deterministic. SVG by templating stays
dependency-light and deterministic. A vega-figures pack could be a later
follow-up for callers who accept the toolchain.
Open questions
Should the figure spec be a new schemas/figure.schema.json, or reuse a finding
or artifact shape already in schemas/?
Centralize the duplicated per-pack figure rule into one shared contract as part
of this work, or keep it per-pack and only reference the new option?
Raster fallback: ship a small deterministic SVG-to-PNG step (resvg or sharp), or
require rasterization at channel-render time? This is a toolchain-versus-
determinism tradeoff.
Does this belong in a new figures pack family, or under an existing family?
Scope
A new opt-in pack and one shared figure contract. No change to the default
Mermaid behavior for callers who do not enable the pack.
An SVG is itself a document (it is XML), so an SVG figure can carry MIF properties
directly: a stable urn:mif: identity, provenance (the findings the figure was
built from), citations, and temporal, embedded in the SVG metadata or a
sidecar. That turns a figure from an opaque asset into a MIF-conformant artifact
whose claims trace to evidence and whose metadata mif-validate can gate.
If those MIF properties prove valuable, the boundary drawn in #226 applies: MIF
Level-1-to-Level-3 document genres live in mif-docs, and non-MIF projections stay
in the harness. A MIF-bearing SVG figure is a MIF document, so the svg-figures
skill would belong in mif-docs (as a genre or a shared helper alongside mif-frontmatter / mif-validate), not as a harness-local figures pack, and the
harness would consume it like the other genres.
Suggested sequence: prototype the MIF-figure first (an SVG plus its MIF identity and
provenance) and see whether the MIF metadata earns its keep. If it does, home the svg-figures skill in mif-docs and have the harness consume it; if figures stay
plain assets with no MIF identity, a harness figures pack is the right home. This
refines the placement open question above.
reacted with thumbs up emoji reacted with thumbs down emoji reacted with laugh emoji reacted with hooray emoji reacted with confused emoji reacted with heart emoji reacted with rocket emoji reacted with eyes emoji
Uh oh!
There was an error while loading. Please reload this page.
Summary
Add a helper pack,
packs/figures/svg-figures, exposing ansvg-figuresskillthat authors self-contained, accessible, brand-consistent SVG figures for
research deliverables, for the figure classes Mermaid cannot express, and wires
them into the report-to-channel pipeline as first-class, MIF-citable artifacts.
Problem and motivation
The harness mandates that every figure be a fenced
mermaidblock: "never ASCIIart, an image link, or Graphviz/DOT", and a required figure is never silently
omitted. That rule buys determinism, provenance-friendliness and portability, and
it should stay the default. The rule is currently duplicated across many pack
SKILL.mdfiles (financial-analysis, competitive-quadrant, sustainability-report,customer-research, market-sizing, trend-modeling and more) rather than living in
one shared contract.
The limitation is expressiveness. Mermaid covers a narrow set (flowcharts,
quadrantChart, sequence, a few others). It cannot produce:real axes, scatter with a trendline, dot and lollipop, small multiples;
competitive-quadrantplots vendors ona
quadrantChartthat cannot place points to a real scale);sankey and flow, heatmaps, KPI and stat panels;
layout, typography and brand color.
A genre that needs one of these has no first-class path: it bends Mermaid past its
limits, describes the figure in prose, or omits it. There is no shared figure
helper, no accessibility contract, no brand contract, and no provenance for
figures. In a MIF harness a chart asserts a claim drawn from findings, so it
should be a citable artifact that traces to its evidence, not an opaque blob.
Proposed solution
A new pack,
packs/figures/svg-figures(one skill per plugin, per the harnessconvention), with an
svg-figuresskill that, given a figure spec plus data drawnfrom findings, emits a deterministic, self-contained, accessible,
brand-consistent SVG.
What it authors. The chart classes Mermaid lacks (listed above), each emitted
as a self-contained SVG: no external fetches, fonts via the system stack, a
responsive
viewBox, and an accessibility contract (role="img",<title>and<desc>, anaria-label, AA contrast, and no color-only encoding, so everyseries carries a pattern, shape or direct label as well as a hue).
Determinism. No
Date.noworMath.randomin the path. An identical specplus data produces byte-identical SVG, so figures diff and round-trip cleanly,
matching the harness determinism posture.
Brand. Figures use the MIF brand tokens (machine-cyan and human-amber on a
dark or light field) through the
mif-brandskill.mif-brandis not currentlyvendored in the template, so the pack should vendor the brand-token subset (or
declare a dependency on it) and never hard-code hex.
MIF integration (the differentiator). A figure is a MIF artifact. The skill
emits the SVG plus a sidecar (or frontmatter) recording
provenance(the findingsor data rows the figure was built from), a caption, and the alt text, so a figure
is citable and its claims trace to evidence, consistent with the report channel
being the MIF Level-3 source of truth.
Channel integration and degradation. SVG inlines directly in
pdf,book,blogand the reports site surface. Where a channel cannot take inline SVG (forexample
notebooklm,jats,xbrl,github-issuesandgithub-discuss), theskill emits a deterministic raster (PNG) fallback or a Mermaid approximation, and
never silently drops a required figure (mirroring the existing rule).
Reconciling with the Mermaid-only rule. Keep Mermaid as the default for the
figures it does well (cheap, inline, no asset). Position SVG as the opt-in path for
figure classes Mermaid cannot represent. Centralize the duplicated per-pack figure
rule into one shared contract that the packs reference, and amend it to: "Mermaid
by default; when the
svg-figurespack is enabled, SVG is permitted for figureclasses Mermaid cannot represent, with a raster fallback for channels that cannot
inline SVG."
Pack mechanics (fits the harness).
packs/figures/svg-figures/ships.claude-plugin/plugin.json(validated againstschemas/pack.schema.json),skills/svg-figures/SKILL.md,evals/evals.jsonandREADME.md. It is toggledthrough
harness.config.jsonpacks[](bash scripts/sync-packs.sh,bash scripts/pack-toggle.sh svg-figures on) and versioned withbash scripts/bump-version.sh --pack figures/svg-figures. The core hardwires nopacks, so it ships off by default.
Acceptance criteria (EARS)
svg-figurespack is enabled, the skill SHALL emit a self-contained SVG thatparses as well-formed XML and carries
<title>,<desc>and anaria-label.SHALL produce byte-identical SVG.
raster fallback and SHALL NOT silently omit a required figure.
built from) so the figure is a citable MIF artifact.
non-color channel (pattern, shape or direct label).
evals/evals.json, itsplugin.jsonSHALL validate againstschemas/pack.schema.json, andbash scripts/verify.shSHALL stay green withthe pack enabled.
Alternatives considered
annotated figures, and its theming is limited.
provenance and portability the harness depends on, which is the reason the
Mermaid-only rule exists.
rendering toolchain into a template that prizes stdlib and no build step, and
raster fonts and anti-aliasing are non-deterministic. SVG by templating stays
dependency-light and deterministic. A
vega-figurespack could be a laterfollow-up for callers who accept the toolchain.
Open questions
schemas/figure.schema.json, or reuse a findingor artifact shape already in
schemas/?of this work, or keep it per-pack and only reference the new option?
require rasterization at channel-render time? This is a toolchain-versus-
determinism tradeoff.
figurespack family, or under an existing family?Scope
A new opt-in pack and one shared figure contract. No change to the default
Mermaid behavior for callers who do not enable the pack.
Note on placement, connecting to #226
An SVG is itself a document (it is XML), so an SVG figure can carry MIF properties
directly: a stable
urn:mif:identity,provenance(the findings the figure wasbuilt from),
citations, andtemporal, embedded in the SVG metadata or asidecar. That turns a figure from an opaque asset into a MIF-conformant artifact
whose claims trace to evidence and whose metadata
mif-validatecan gate.If those MIF properties prove valuable, the boundary drawn in #226 applies: MIF
Level-1-to-Level-3 document genres live in
mif-docs, and non-MIF projections stayin the harness. A MIF-bearing SVG figure is a MIF document, so the
svg-figuresskill would belong in
mif-docs(as a genre or a shared helper alongsidemif-frontmatter/mif-validate), not as a harness-localfigurespack, and theharness would consume it like the other genres.
Suggested sequence: prototype the MIF-figure first (an SVG plus its MIF identity and
provenance) and see whether the MIF metadata earns its keep. If it does, home the
svg-figuresskill inmif-docsand have the harness consume it; if figures stayplain assets with no MIF identity, a harness
figurespack is the right home. Thisrefines the placement open question above.
Opened from issue #225 and moved here as an idea.
All reactions