Every change Wellknown observed on this MCP server, newest first, with what it was before and what it became. Tool-surface changes carry the definition diff. Nothing here is edited after the fact.
Changed the definition of "artifact_certify", "catalog_list", "design_preview" and 6 more
Certify a chart from its viz_renderDrawinput,andgivencertifyasa chart:the pinned package draws it and certifiesfrom thenormalizedSpec it returns,input inthe same brand and themechart,with theusing matching datafor an ECharts,type.brandTheandreplytheme.hasReturns the samecontentresult asviz_render’s for that input, the drawing beside the verdictviz_render:conformant, coveragehashes,findingswarnings and thefourcertificationpillarsverdict, including accessibility equivalence, determinism, contrast and accuracy.A certified chartOptionalcanchart.outputbefieldsconformant:addfalseSVG,so read each pillar. viz_render already certifiesthewhataccessibleittabledraws;andcallnarrative,thisorwhentheyounormalizedwantspecification.theA verdictbycanname.beCertifyingconformantafalse;normalizedeachspecpillaronexplains itsown belongs to the local package.result.
before
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact_certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"additionalProperties":false,"properties":{"chart":{"$id":"https://oods-foundry.com/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"Checks the drawn chart's accessible equivalents as it is rendered; on by default. For Vega-Lite charts, a rule marked error stops the render (status error, with one OODS-<rule id> code per rule in errors), and a rule marked warn is reported in warnings. Charts built from rows and encodings always pass. Set false only for a spec you supply that is known not to conform. ECharts-primary charts are not checked here, because their scaffold has no data yet.","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used instead of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link must carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used instead of rows + x/y encodings. Carries inline geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination arcs for flow_map. Geometry is supplied inline — it is never fetched over the network. Note: geo specs are not self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the destination latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the destination longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the origin latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the origin longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used instead of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list","type":"string"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested","type":"string"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"Structured (typed, not free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it instead of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive encoding, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (not a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 tabular marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used instead of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link must reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' must match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used instead of rows + x/y encodings. Nodes plus value-weighted links; every link must carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Strict field checks. When true, a data key that does not resolve is reported in warnings instead of producing a silently wrong chart: an encoding that names a field missing from every non-empty row (OODS-V131), or a choropleth region whose join key matches no map feature (OODS-V134, one per unmatched region). The default, false, keeps the current behavior, which drops unmatched map regions silently. Dashboard_render has its own strictFields, which turns OODS-V131 into an error panel through its onPanelError option.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}},"required":["chart"],"type":"object"}{"destructiveHint":false,"idempotentHint":true,"openWorldHint":false,"readOnlyHint":true,"title":"Certify Chart"}
List the pinned registry’sRead components,a page at a time. category, traitand, contextfilter the list (each reply’s availableCategories names the categories);and statusfilters by eachfiltercomponent’stheHTML-rendererlist; status,not its ReactdescribesortheVueHTMLreadiness.renderer. detailsets each entry’s size:is brief(name, categories and one readiness label; the
Find a screen OODS FoundryLookgeneratedupatatherecordedpinnedscreenversion:by objectand, contextpick one of the recorded object screens,andframework its React or Vue app.framework. Returnsthe URL on oods-foundry.com where thatitsbuiltrunningappscreenrunsURL,
CheckRead theOODS Foundry process behind these tools:runningitsservice status,packagepinned versionand uptime, registry counts(components,objects, traits), thebuilt brands, themesand, token scopes,andtheretained proofsummaries, each naming the release it measured. Use it first, to learn the pinned version; usesummaries.catalog_list,Uptimeobject_registryandorlatencyregistry_snapshot
Read objects from the pinnedregistry’s objects.registry. action list returnsthe objects in use, business objects first, each with its sourcenames, traits and fieldcount;counts; domain, trait and maturity filteritthem, and includeInternal addsOODS Foundry’sinternalobjects, which hiddenInternal counts otherwise.objects. action show,withrequires name,returns one object’s composed definition: traits, fieldsandtheir semantics, view extensions by context,returnstokensitsand
Read thepinned package'sregistry summaryin one reply:everyactiveobjectobjects andtrait, keyed by nametraits,with the registry'sloaded names,anyloader issues,a canonicaletag and generatedAt.The default summary omits schemas, view extensions and tokens.detail fullreturns completeincludes definitions; nameslimits the objects and traitsnarrowstothem.thoseincludeInternalnames.addsAinternal
Fetch one registry dataset as a single export: dataset componentsRead(thelive registry’s components, objects and traits),tokens ormanifest. The replymanifestcarriesdataset,thewithexport’sits versiondate,anetag, sizeBytes andthepayload.An export larger than this endpoint’s 100,000-character reply bound, as components is at this version, is refused with its size;includePayload:false returnsits version, etag and sizemetadataalone.only. listVersionsreturns the dated exports instead of a
Readthe full JSON Schema of any OODSaFoundryshipped toolat the pinned version, as the package shipsschemait:by nameis any of its tools, local-only ones included,and kindis input(the default)input oroutput.output). Returnsthe schema,itsfileJSONinSchema,thepackage-relativepackagefile,thatrecorded
Drawa chart with the pinned OODS Foundryand certifyit, in oneacall.chartGivefrom inlinerowsdata.withProvide chartType andencodings; a pattern idencodingstowithdrawrows, acatalog chartpattern with its ownrows; an intent (goal, measuresdata,dimensions) instead of encodings;orrows withoutanchartType
Changed the definition of "artifact_certify", "object_registry", "registry_snapshot" and 2 more
before
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact.certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"additionalProperties":false,"properties":{"chart":{"$id":"https://designlab.local/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"A11y equivalence CERTIFY-AT-EMISSION switch. DEFAULT ON. The cartesian (Vega-Lite) emission is checked against the accessible-equivalence engine (validateVizEquivalenceRules): error-severity rules BLOCK (status:'error' with per-rule OODS-<rule.id> codes in `errors`), warn-severity failures surface in `warnings` as OODS-<rule.id>. Default builder output is conformant-BY-CONSTRUCTION , so generated specs pass; set false to opt out for agent-supplied non-conformant specs. Scoped to the cartesian path (the ECharts-primary scaffold has empty data and would spuriously fail data-equivalence rules).","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used INSTEAD of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link MUST carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used INSTEAD of rows + x/y encodings. Carries INLINE geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination ARCS for flow_map. Geometry is supplied INLINE — it is never fetched over the network. NOTE: geo specs are NOT self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the DESTINATION latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the DESTINATION longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the ORIGIN latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the ORIGIN longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used INSTEAD of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"STRUCTURED (typed, NOT free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it INSTEAD of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive ENCODING, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (NOT a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 TABULAR marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used INSTEAD of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link MUST reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' MUST match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used INSTEAD of rows + x/y encodings. Nodes plus value-weighted links; every link MUST carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Field/key-presence STRICT switch. When true, a referenced data key that does not resolve is surfaced in `warnings` instead of a silent confident-wrong result: (m05) an explicit tabular chart whose encoding references a field ABSENT from every (non-empty) row → OODS-V131; (m06) a choropleth corridor whose join key has NO matching map feature → OODS-V134 (per unmatched corridor). DEFAULT false keeps today's behavior byte-identical (the geo silent-drop preserved). The dashboard.render strict check (its own `strictFields`) escalates V131 to an error panel via `onPanelError`.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}},"required":["chart"],"type":"object"}Changed the definition of "catalog_list" and "registry_snapshot"
⟨8 unchanged words⟩ "Filter components by category (e.g., 'core','data''lifecycle', 'visual')","type":"string"},"context": ⟨159 unchanged words⟩
Readan overview ofthewholepinned package's registry summary in one reply: every active object(domain, description, tags, the traits it uses
Changed the definition of "artifact_certify", "catalog_list", "design_preview" and 5 more
⟨82 unchanged words⟩ this when you want the verdict by name.To certifyCertifying a normalized spec on its own,usebelongs to the localstdio.package.
before
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact.certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"nonPatternInput":{"allOf":[{"if":{"properties":{"chartType":{"enum":["bar","line","area","scatter","heatmap"]}},"required":["chartType"]},"then":{"properties":{"encodings":{"required":["x","y"]}},"required":["encodings"]}},{"if":{"properties":{"chartType":{"enum":["treemap","sunburst"]}},"required":["chartType"]},"then":{"required":["hierarchy"]}},{"if":{"properties":{"chartType":{"const":"sankey"}},"required":["chartType"]},"then":{"required":["sankey"]}},{"if":{"properties":{"chartType":{"const":"force_graph"}},"required":["chartType"]},"then":{"required":["network"]}},{"if":{"properties":{"chartType":{"const":"choropleth"}},"required":["chartType"]},"then":{"properties":{"geo":{"anyOf":[{"required":["geojson"]},{"required":["topojson"]}],"required":["valueField"]}},"required":["geo"]}},{"if":{"properties":{"chartType":{"const":"bubble_map"}},"required":["chartType"]},"then":{"properties":{"geo":{"required":["longitudeField","latitudeField","rows"]}},"required":["geo"]}},{"if":{"properties":{"chartType":{"const":"flow_map"}},"required":["chartType"]},"then":{"properties":{"geo":{"anyOf":[{"required":["geojson"]},{"required":["topojson"]}],"required":["originLongitudeField","originLatitudeField","destinationLongitudeField","destinationLatitudeField","rows"]}},"required":["geo"]}},{"if":{"properties":{"chartType":{"const":"chord"}},"required":["chartType"]},"then":{"required":["chord"]}}],"oneOf":[{"required":["rows"]},{"required":["datasetRef"]},{"required":["hierarchy"]},{"required":["sankey"]},{"required":["chord"]},{"required":["network"]},{"required":["geo"]}]}},"additionalProperties":false,"properties":{"chart":{"$id":"https://designlab.local/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"allOf":[{"if":{"not":{"required":["pattern"]}},"then":{"$ref":"#/$defs/nonPatternInput"}}],"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows/datasetRef for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"A11y equivalence CERTIFY-AT-EMISSION switch. DEFAULT ON. The cartesian (Vega-Lite) emission is checked against the accessible-equivalence engine (validateVizEquivalenceRules): error-severity rules BLOCK (status:'error' with per-rule OODS-<rule.id> codes in `errors`), warn-severity failures surface in `warnings` as OODS-<rule.id>. Default builder output is conformant-BY-CONSTRUCTION , so generated specs pass; set false to opt out for agent-supplied non-conformant specs. Scoped to the cartesian path (the ECharts-primary scaffold has empty data and would spuriously fail data-equivalence rules).","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows/datasetRef with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link MUST carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. Carries INLINE geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination ARCS for flow_map. Geometry is supplied INLINE — it is never fetched over the network. NOTE: geo specs are NOT self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the DESTINATION latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the DESTINATION longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the ORIGIN latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the ORIGIN longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"STRUCTURED (typed, NOT free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it INSTEAD of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive ENCODING, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick, and an optional governed `measureRef` lights the governed-measure narrative overlay (only when output.includeA11y=true). Requires `rows` (or a `datasetRef`).","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (NOT a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 TABULAR marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link MUST reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' MUST match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, datasetRef, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. Nodes plus value-weighted links; every link MUST carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Field/key-presence STRICT switch. When true, a referenced data key that does not resolve is surfaced in `warnings` instead of a silent confident-wrong result: (m05) an explicit tabular chart whose encoding references a field ABSENT from every (non-empty) row → OODS-V131; (m06) a choropleth corridor whose join key has NO matching map feature → OODS-V134 (per unmatched corridor). DEFAULT false keeps today's behavior byte-identical (the geo silent-drop preserved). The dashboard.render strict check (its own `strictFields`) escalates V131 to an error panel via `onPanelError`.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}},"required":["chart"],"type":"object"}Changed the definition of "tool_schema"
⟨28 unchanged words⟩ component_map","schema_store","object_registry","schema_render","object_import","a11y_scan"],"type":"string"}},"required ⟨3 unchanged words⟩
Certificate recorded, valid to 2026-12-21
Authorization not required
Added "health_check", "object_registry" and "structured_data_fetch"; removed "health", "object" and "structuredData_fetch"; changed the definition of "artifact_certify", "catalog_list", "design_preview" and 3 more
before
—after
Certify ChartCertify a chartthrough the same route. Supplyfrom its viz_render input,ingivenchart;as chart: theroutepinned package
Unknown → Live
First tool surface recorded: 9 tools (server version 0.6.2)
https://oods-foundry.com/mcp (mcp_streamable_http) — from mcp_registry
npm:@oods/foundry (package_npm) — from mcp_registry, with the record
Showing the latest 12 events. The API returns up to 500 and filters by kind: ?kind=tool_surface_changed
after
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}],"type":["string","object"]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}],"type":["string","object"]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact_certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}],"type":["string","object"]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}],"type":["string","object"]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode","type":"object"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"additionalProperties":false,"properties":{"chart":{"additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"Checks the drawn chart's accessible equivalents as it is rendered; on by default. For Vega-Lite charts, a rule marked error stops the render (status error, with one OODS-<rule id> code per rule in errors), and a rule marked warn is reported in warnings. Charts built from rows and encodings always pass. Set false only for a spec you supply that is known not to conform. ECharts-primary charts are not checked here, because their scaffold has no data yet.","type":"boolean"},"brand":{"default":"A","description":"Token brand for drawing and certification.","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used instead of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link must carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used instead of rows + x/y encodings. Carries inline geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination arcs for flow_map. Geometry is supplied inline — it is never fetched over the network. Note: geo specs are not self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the destination latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the destination longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the origin latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the origin longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used instead of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list","type":"string"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode","type":"object"},"type":{"const":"nested","type":"string"}},"required":["type","data"],"type":"object"}],"type":"object"},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"Structured (typed, not free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it instead of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive encoding, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (not a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 tabular marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used instead of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link must reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' must match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"description":"Optional drawing and accessibility outputs; the default reply contains hashes and certification.","properties":{"height":{"description":"Drawing height in pixels.","maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"default":false,"description":"Include the accessible data table and narrative.","type":"boolean"},"includeNormalizedSpec":{"default":false,"description":"Include the normalized chart specification.","type":"boolean"},"svg":{"default":false,"description":"Include the SVG drawing, for displaying the chart.","type":"boolean"},"width":{"description":"Drawing width in pixels.","maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used instead of rows + x/y encodings. Nodes plus value-weighted links; every link must carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Strict field checks. When true, a data key that does not resolve is reported in warnings instead of producing a silently wrong chart: an encoding that names a field missing from every non-empty row (OODS-V131), or a choropleth region whose join key matches no map feature (OODS-V134, one per unmatched region). The default, false, keeps the current behavior, which drops unmatched map regions silently. Dashboard_render has its own strictFields, which turns OODS-V131 into an error panel through its onPanelError option.","type":"boolean"},"theme":{"default":"light","description":"Colour theme for drawing and certification.","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"},"reproduce":{"default":false,"description":"Include the command and calls for reproducing this result.","type":"boolean"}},"required":["chart"],"type":"object"}{"$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"properties":{"category":{" ⟨122 unchanged words⟩ ":200,"minimum":1,"type":"integer"},"reproduce":{"default":false,"description":"Include the command and calls for reproducing this result.","type":"boolean"},"status":{"description":"Filter by ⟨40 unchanged words⟩
{"destructiveHint":false,"idempotentHint":true,"openWorldHint":false,"readOnlyHint":true,"title":"List Components"}
⟨59 unchanged words⟩ Usage","User"],"type":"string"},"reproduce":{"default":false,"description":"Include the command and calls for reproducing this result.","type":"boolean"}},"required":["object"],"type":"object"}
{"destructiveHint":false,"idempotentHint":true,"openWorldHint":false,"readOnlyHint":true,"title":"Look Up Recorded Screen"}
{"$schema":"http://json-schema.org/draft-07/schema#","additionalProperties":false,"properties":{"includeChangelog":{" ⟨4 unchanged words⟩ true, include DSL version changelog in the response.","type":"boolean"},"reproduce":{"default":false,"description":"Include the command and calls for reproducing this result.","type":"boolean"},"sinceVersion":{ ⟨16 unchanged words⟩
{"destructiveHint":false,"idempotentHint":true,"openWorldHint":false,"readOnlyHint":true,"title":"Check Health"}
{"$schema":"http://json-schema.org/draft-07/schema#","additionalProperties":false,"description":"Read object definitions ⟨104 unchanged words⟩ ^[A-Za-z][A-Za-z0-9_-]*$","type":"string"},"reproduce":{"default":false,"description":"Include the command and calls for reproducing this result.","type":"boolean"},"trait":{"description":"Filter to ⟨17 unchanged words⟩
{"destructiveHint":false,"idempotentHint":true,"openWorldHint":false,"readOnlyHint":true,"title":"Read Object Registry"}
{"$id":"https://oods-foundry.com/schemas/registry.snapshot.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Bulk-read recorded mappings ⟨115 unchanged words⟩ :1,"type":"array","uniqueItems":true},"reproduce":{"default":false,"description":"Include the command and calls for reproducing this result.","type":"boolean"}},"title":"registry_snapshot input","type":"object"}
{"destructiveHint":false,"idempotentHint":true,"openWorldHint":false,"readOnlyHint":true,"title":"Snapshot Registry"}
{"$id":"structuredData.fetch.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Read a pinned ⟨10 unchanged words⟩ "Registry dataset to return.","enum":["components","tokens","manifest"],"type":"string"} ⟨10 unchanged words⟩ "minLength":8,"type":"string"},"includeInternalincludePayload":{"default":falsetrue,"description":"Live components dataset only: also list OODS Foundry's internal (non-business)Whenobjectsfalse,after the business objects. Without it they are left out and registry.hiddenInternal countsomitthem;payloadaevendatedifexportnoisETagservedmatchunchanged.occurs.","type":"boolean"},"includePayloadlistVersions":{"default":truefalse,"description":"Whenfalsetrue,omit payloadreturnevenavailableifversionnodatesETaginsteadmatchofoccurs.payload.","type":"boolean"},"listVersionsreproduce":{"default":false,"description":"WhenIncludetrue,thereturncommandavailableandversioncallsdatesforinsteadreproducingofthispayload.result.","type":"boolean"},"version":{ ⟨34 unchanged words⟩
{"destructiveHint":false,"idempotentHint":true,"openWorldHint":false,"readOnlyHint":true,"title":"Fetch Structured Data"}
⟨33 unchanged words⟩ tokens_build","structured_data_fetch","brand_apply","brand_create","brand_read","catalog_list","code_generate","design_compose","design_preview","design_versions","pipeline_run","health_check","registry_snapshot","viz_render","dashboard_render","artifact_certify","fidelity_preview","component_map","component_map_read","schema_store","schema_read","object_registry","object_register","schema_render","object_import","object_import_read","a11y_scan"],"type":"string"},"reproduce":{"default":false,"description":"Include the command and calls for reproducing this result.","type":"boolean"}},"required":["name"],"type":"object"}
{"destructiveHint":false,"idempotentHint":true,"openWorldHint":false,"readOnlyHint":true,"title":"Read Tool Schema"}
before
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact_certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"$id":"https://oods-foundry.com/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"Checks the drawn chart's accessible equivalents as it is rendered; on by default. For Vega-Lite charts, a rule marked error stops the render (status error, with one OODS-<rule id> code per rule in errors), and a rule marked warn is reported in warnings. Charts built from rows and encodings always pass. Set false only for a spec you supply that is known not to conform. ECharts-primary charts are not checked here, because their scaffold has no data yet.","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used instead of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link must carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used instead of rows + x/y encodings. Carries inline geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination arcs for flow_map. Geometry is supplied inline — it is never fetched over the network. Note: geo specs are not self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the destination latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the destination longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the origin latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the origin longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used instead of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list","type":"string"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested","type":"string"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"Structured (typed, not free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it instead of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive encoding, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (not a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 tabular marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used instead of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link must reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' must match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used instead of rows + x/y encodings. Nodes plus value-weighted links; every link must carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Strict field checks. When true, a data key that does not resolve is reported in warnings instead of producing a silently wrong chart: an encoding that names a field missing from every non-empty row (OODS-V131), or a choropleth region whose join key matches no map feature (OODS-V134, one per unmatched region). The default, false, keeps the current behavior, which drops unmatched map regions silently. Dashboard_render has its own strictFields, which turns OODS-V131 into an error panel through its onPanelError option.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}after
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}],"type":["string","object"]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}],"type":["string","object"]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact_certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}],"type":["string","object"]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}],"type":["string","object"]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode","type":"object"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"Checks the drawn chart's accessible equivalents as it is rendered; on by default. For Vega-Lite charts, a rule marked error stops the render (status error, with one OODS-<rule id> code per rule in errors), and a rule marked warn is reported in warnings. Charts built from rows and encodings always pass. Set false only for a spec you supply that is known not to conform. ECharts-primary charts are not checked here, because their scaffold has no data yet.","type":"boolean"},"brand":{"default":"A","description":"Token brand for drawing and certification.","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used instead of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link must carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used instead of rows + x/y encodings. Carries inline geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination arcs for flow_map. Geometry is supplied inline — it is never fetched over the network. Note: geo specs are not self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the destination latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the destination longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the origin latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the origin longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used instead of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list","type":"string"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode","type":"object"},"type":{"const":"nested","type":"string"}},"required":["type","data"],"type":"object"}],"type":"object"},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"Structured (typed, not free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it instead of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive encoding, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (not a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 tabular marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used instead of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link must reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' must match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"description":"Optional drawing and accessibility outputs; the default reply contains hashes and certification.","properties":{"height":{"description":"Drawing height in pixels.","maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"default":false,"description":"Include the accessible data table and narrative.","type":"boolean"},"includeNormalizedSpec":{"default":false,"description":"Include the normalized chart specification.","type":"boolean"},"svg":{"default":false,"description":"Include the SVG drawing, for displaying the chart.","type":"boolean"},"width":{"description":"Drawing width in pixels.","maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"reproduce":{"default":false,"description":"Include the command and calls for reproducing this result.","type":"boolean"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used instead of rows + x/y encodings. Nodes plus value-weighted links; every link must carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Strict field checks. When true, a data key that does not resolve is reported in warnings instead of producing a silently wrong chart: an encoding that names a field missing from every non-empty row (OODS-V131), or a choropleth region whose join key matches no map feature (OODS-V134, one per unmatched region). The default, false, keeps the current behavior, which drops unmatched map regions silently. Dashboard_render has its own strictFields, which turns OODS-V131 into an error panel through its onPanelError option.","type":"boolean"},"theme":{"default":"light","description":"Colour theme for drawing and certification.","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}{"destructiveHint":false,"idempotentHint":true,"openWorldHint":false,"readOnlyHint":true,"title":"Render Chart"}
after
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact_certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"additionalProperties":false,"properties":{"chart":{"$id":"https://oods-foundry.com/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"Checks the drawn chart's accessible equivalents as it is rendered; on by default. For Vega-Lite charts, a rule marked error stops the render (status error, with one OODS-<rule id> code per rule in errors), and a rule marked warn is reported in warnings. Charts built from rows and encodings always pass. Set false only for a spec you supply that is known not to conform. ECharts-primary charts are not checked here, because their scaffold has no data yet.","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used instead of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link must carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used instead of rows + x/y encodings. Carries inline geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination arcs for flow_map. Geometry is supplied inline — it is never fetched over the network. Note: geo specs are not self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the destination latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the destination longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the origin latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the origin longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used instead of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list","type":"string"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested","type":"string"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"Structured (typed, not free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it instead of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive encoding, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (not a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 tabular marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used instead of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link must reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' must match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used instead of rows + x/y encodings. Nodes plus value-weighted links; every link must carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Strict field checks. When true, a data key that does not resolve is reported in warnings instead of producing a silently wrong chart: an encoding that names a field missing from every non-empty row (OODS-V131), or a choropleth region whose join key matches no map feature (OODS-V134, one per unmatched region). The default, false, keeps the current behavior, which drops unmatched map regions silently. Dashboard_render has its own strictFields, which turns OODS-V131 into an error panel through its onPanelError option.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}},"required":["chart"],"type":"object"}⟨22 unchanged words⟩ definition.","enum":["list","show"],"type":"string"},"context":{"description":"Optional: filter ⟨101 unchanged words⟩ ,"required":["action"],"title":"objectobject_registry input","type":"object"}
{"$id":"https://designlab.local/schemas/registry.snapshot.input.json//oods-foundry.com/schemas/registry.snapshot.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties": ⟨122 unchanged words⟩ array","uniqueItems":true}},"title":"registry.snapshotregistry_snapshot input","type":"object"}
⟨141 unchanged words⟩ ,"required":["dataset"],"title":"structuredData.fetchstructured_data_fetch input","type":"object"}
before
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact.certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"$id":"https://designlab.local/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"A11y equivalence CERTIFY-AT-EMISSION switch. DEFAULT ON. The cartesian (Vega-Lite) emission is checked against the accessible-equivalence engine (validateVizEquivalenceRules): error-severity rules BLOCK (status:'error' with per-rule OODS-<rule.id> codes in `errors`), warn-severity failures surface in `warnings` as OODS-<rule.id>. Default builder output is conformant-BY-CONSTRUCTION , so generated specs pass; set false to opt out for agent-supplied non-conformant specs. Scoped to the cartesian path (the ECharts-primary scaffold has empty data and would spuriously fail data-equivalence rules).","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used INSTEAD of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link MUST carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used INSTEAD of rows + x/y encodings. Carries INLINE geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination ARCS for flow_map. Geometry is supplied INLINE — it is never fetched over the network. NOTE: geo specs are NOT self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the DESTINATION latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the DESTINATION longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the ORIGIN latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the ORIGIN longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used INSTEAD of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"STRUCTURED (typed, NOT free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it INSTEAD of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive ENCODING, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (NOT a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 TABULAR marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used INSTEAD of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link MUST reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' MUST match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used INSTEAD of rows + x/y encodings. Nodes plus value-weighted links; every link MUST carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Field/key-presence STRICT switch. When true, a referenced data key that does not resolve is surfaced in `warnings` instead of a silent confident-wrong result: (m05) an explicit tabular chart whose encoding references a field ABSENT from every (non-empty) row → OODS-V131; (m06) a choropleth corridor whose join key has NO matching map feature → OODS-V134 (per unmatched corridor). DEFAULT false keeps today's behavior byte-identical (the geo silent-drop preserved). The dashboard.render strict check (its own `strictFields`) escalates V131 to an error panel via `onPanelError`.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}after
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact_certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"$id":"https://oods-foundry.com/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"Checks the drawn chart's accessible equivalents as it is rendered; on by default. For Vega-Lite charts, a rule marked error stops the render (status error, with one OODS-<rule id> code per rule in errors), and a rule marked warn is reported in warnings. Charts built from rows and encodings always pass. Set false only for a spec you supply that is known not to conform. ECharts-primary charts are not checked here, because their scaffold has no data yet.","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used instead of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link must carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used instead of rows + x/y encodings. Carries inline geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination arcs for flow_map. Geometry is supplied inline — it is never fetched over the network. Note: geo specs are not self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the destination latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the destination longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the origin latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the origin longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used instead of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list","type":"string"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested","type":"string"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"Structured (typed, not free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it instead of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive encoding, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (not a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 tabular marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name must exist among the data rows' fields. `type` is reserved in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used instead of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link must reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' must match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used instead of rows + x/y encodings. Nodes plus value-weighted links; every link must carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Strict field checks. When true, a data key that does not resolve is reported in warnings instead of producing a silently wrong chart: an encoding that names a field missing from every non-empty row (OODS-V131), or a choropleth region whose join key matches no map feature (OODS-V134, one per unmatched region). The default, false, keeps the current behavior, which drops unmatched map regions silently. Dashboard_render has its own strictFields, which turns OODS-V131 into an error panel through its onPanelError option.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}⟨21 unchanged words⟩ Reports definition loader issues, including shadowed names. The default summary leaves out each trait's and object's schema, parameters, view extensions, semantics, tokens and metadata; detail full returns them, optionally only for named traits and objects. Draft preferred_terms, disambiguation_decisions and capabilities are not snapshot outputs.","properties":{"detail":{"default":"summary","description":"summary (default), or full definitions, best with names.","enum":["summary","full"],"type":"string"},"includeInternal":{"default":false,"description":"Also ⟨16 unchanged words⟩ and registry.hiddenInternal counts them.","type":"boolean"},"names":{"description":"Exact trait and object names; misses go in notFound.","items":{"minLength":1,"type":"string"},"minItems":1,"type":"array","uniqueItems":true}},"title":"registry.snapshot input","type":"object"}
after
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact.certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"additionalProperties":false,"properties":{"chart":{"$id":"https://designlab.local/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"A11y equivalence CERTIFY-AT-EMISSION switch. DEFAULT ON. The cartesian (Vega-Lite) emission is checked against the accessible-equivalence engine (validateVizEquivalenceRules): error-severity rules BLOCK (status:'error' with per-rule OODS-<rule.id> codes in `errors`), warn-severity failures surface in `warnings` as OODS-<rule.id>. Default builder output is conformant-BY-CONSTRUCTION , so generated specs pass; set false to opt out for agent-supplied non-conformant specs. Scoped to the cartesian path (the ECharts-primary scaffold has empty data and would spuriously fail data-equivalence rules).","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used INSTEAD of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link MUST carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used INSTEAD of rows + x/y encodings. Carries INLINE geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination ARCS for flow_map. Geometry is supplied INLINE — it is never fetched over the network. NOTE: geo specs are NOT self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the DESTINATION latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the DESTINATION longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the ORIGIN latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the ORIGIN longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used INSTEAD of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"STRUCTURED (typed, NOT free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it INSTEAD of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive ENCODING, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (NOT a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 TABULAR marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used INSTEAD of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link MUST reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' MUST match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used INSTEAD of rows + x/y encodings. Nodes plus value-weighted links; every link MUST carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Field/key-presence STRICT switch. When true, a referenced data key that does not resolve is surfaced in `warnings` instead of a silent confident-wrong result: (m05) an explicit tabular chart whose encoding references a field ABSENT from every (non-empty) row → OODS-V131; (m06) a choropleth corridor whose join key has NO matching map feature → OODS-V134 (per unmatched corridor). DEFAULT false keeps today's behavior byte-identical (the geo silent-drop preserved). The dashboard.render strict check (its own `strictFields`) escalates V131 to an error panel via `onPanelError`.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}},"required":["chart"],"type":"object"}⟨19 unchanged words⟩ availableCategories names the categories); status filters bytheeachlegacycomponent’sstatic-HTMLHTML-renderer status,only.not its React or Vue readiness. detail sets each entry’s size: brief (name, ⟨27 unchanged words⟩ ). page and pageSize walk through totalCount, and hasMore says whether another page follows: up to 200 a page,andathasMorebriefsaysorwhethersummary,anotherandpageupfollows.toUse10itattofull,choosewhichcomponents;isusealsostructured_data_fetchthewithpagedatasetsizecomponentsthereinsteadwhenfornonetheiswholegiven.exportUseinitonetoreplychoose components, and object_registry for objects. Read-only.
⟨45 unchanged words⟩ it was generated in, and the threelocalcalls that reproduce it with the local package (brand_create, design_compose, code_generate). Nothing is composed or generated here;fora live preview of your own composition,callbelongsdesign_previewtooverthe localstdio.package. Use object_registry show instead to read the definition behind a screen.
⟨3 unchanged words⟩ :{"context":{"default":"detail","description":"The context the screen was composed for.","enum":["detail","list","form", ⟨6 unchanged words⟩ },"framework":{"default":"react","description":"The framework of the generated app.","enum":["react","vue"],"type":"string"},"object":{"description":"An object with recorded screens at this version.","enum":["Article","Invoice","Media" ⟨14 unchanged words⟩
⟨65 unchanged words⟩ extensions to one context. Use registry_snapshot instead for an overview of every object and traitin one reply, and design_preview to see a generated screen ⟨6 unchanged words⟩ show answer here; validate, register and reloadneedbelong to the localstdio.package.
{"$schema":"http://json-schema.org/draft-07/schema#","allOfadditionalProperties":[{false,"ifdescription":{"Read object definitions from the pinned registry.","properties":{"action":{"constdescription":"listList objects or show one composed definition."}},"requiredenum":["actionlist","show"]},"thencontext":{"additionalPropertiesdescription":false,"properties"Optional:{"actionfilter view_extensions to a single context (e.g. 'detail', 'list', 'form', 'timeline', 'card', 'inline')":{,"consttype":"liststring"},"domain":{"description":"Filter to ⟨48 unchanged words⟩ ,"stable"],"type":"string"},"trait":{"description":"Filter to objects composing a given trait (e.g. 'Priceable', 'lifecycle/Stateful')","type":"string"}},"type":"object"}},{"if":{"properties":{"action":{"const":"show"}},"required":["action"]},"then":{"additionalProperties":false,"properties":{"action":{"const":"show"},"context":{"description":"Optional: filter view_extensions to a single context (e.g. 'detail', 'list', 'form', 'timeline', 'card', 'inline')","type":"string"},"name":{"description":"Object name to look ⟨7 unchanged words⟩ A-Za-z][A-Za-z0-9_-]*$","type":"string"}},"required":["name"],"typetrait":"object"}}],{"description":"Read object definitions fromFilterthetopinnedobjectsregistry.","properties":{"action":{"description":"Listcomposingobjectsaorgivenshowtraitone(e.g.composed'Priceable',definition.'lifecycle/Stateful')","enumtype":["list","showstring"]}},"required":["action"],"title" ⟨4 unchanged words⟩
Read an overview of the whole pinned registry in one reply: every active object (fieldsdomain,semanticsdescription,tokenstags, the traits it uses and its field names) and everytrait’straitfull(category,definitiondescription, tags, contexts and the objects that use it), keyed by name, with therecorded component mappingsregistry’s(noneloadedonnames,thisanyhostedloaderprocess)issues, a canonical etag and generatedAt.registryThenamesfullthesnapshot,livewithsourceevery semantic,thetoken,loadedparameter and view extension, is larger than this endpoint’s 100,000-character reply bound; overview names what this reply leaves out andanytheloaderfullissues;snapshot’s size. includeInternal adds OODS Foundry’s internal objects, which registry.hiddenInternal counts otherwise. Use object_registry show instead for one object’s composed definitionwith its view extensions, and catalog_list for components. Read-only, with no ⟨9 unchanged words⟩
⟨26 unchanged words⟩ date, an etag, sizeBytes and the payload. An export larger than this endpoint’s 100,000-character reply bound, as components is at this version, is refused with its size; includePayload: false returns its version, etag and size alone. listVersions returns the dated exports instead of a ⟨28 unchanged words⟩ matched: true and no payload when nothingchanged; includePayload: false omits the payload anyway.changed. includeInternal applies to components only. Use catalog_list instead tofilterread components a page at atime. Read-only; the Stage1time,runandkindsobject_registryneedforlocalobjects.stdio.Read-only.
⟨47 unchanged words⟩ and its URL on this site. Use itbefore calling a tool over local stdio, orto learn what a tool accepts or returns: these hosted tools declare no output schema, and tools/list here shows narrower inputs than the localstdiopackage accepts.
⟨3 unchanged words⟩ :{"kind":{"default":"input","description":"The tool's input schema or its output schema.","enum":["input","output"],"type":"string"},"name":{"description":"Any OODS Foundry tool at this version, local-only tools included.","enum":["tokens_build","structured_data_fetch","brand_apply" ⟨24 unchanged words⟩
⟨104 unchanged words⟩ artifact_certify returns the same reply. Inline data only(no datasetRef or measureRef), up to 500 rows; the same input returns the same bytes. A reply larger than this endpoint’s 100,000-character bound, such as a pattern drawn with all its rows, is refused with its size.
before
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact.certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"nonPatternInput":{"allOf":[{"if":{"properties":{"chartType":{"enum":["bar","line","area","scatter","heatmap"]}},"required":["chartType"]},"then":{"properties":{"encodings":{"required":["x","y"]}},"required":["encodings"]}},{"if":{"properties":{"chartType":{"enum":["treemap","sunburst"]}},"required":["chartType"]},"then":{"required":["hierarchy"]}},{"if":{"properties":{"chartType":{"const":"sankey"}},"required":["chartType"]},"then":{"required":["sankey"]}},{"if":{"properties":{"chartType":{"const":"force_graph"}},"required":["chartType"]},"then":{"required":["network"]}},{"if":{"properties":{"chartType":{"const":"choropleth"}},"required":["chartType"]},"then":{"properties":{"geo":{"anyOf":[{"required":["geojson"]},{"required":["topojson"]}],"required":["valueField"]}},"required":["geo"]}},{"if":{"properties":{"chartType":{"const":"bubble_map"}},"required":["chartType"]},"then":{"properties":{"geo":{"required":["longitudeField","latitudeField","rows"]}},"required":["geo"]}},{"if":{"properties":{"chartType":{"const":"flow_map"}},"required":["chartType"]},"then":{"properties":{"geo":{"anyOf":[{"required":["geojson"]},{"required":["topojson"]}],"required":["originLongitudeField","originLatitudeField","destinationLongitudeField","destinationLatitudeField","rows"]}},"required":["geo"]}},{"if":{"properties":{"chartType":{"const":"chord"}},"required":["chartType"]},"then":{"required":["chord"]}}],"oneOf":[{"required":["rows"]},{"required":["datasetRef"]},{"required":["hierarchy"]},{"required":["sankey"]},{"required":["chord"]},{"required":["network"]},{"required":["geo"]}]}},"$id":"https://designlab.local/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"allOf":[{"if":{"not":{"required":["pattern"]}},"then":{"$ref":"#/$defs/nonPatternInput"}}],"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows/datasetRef for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"A11y equivalence CERTIFY-AT-EMISSION switch. DEFAULT ON. The cartesian (Vega-Lite) emission is checked against the accessible-equivalence engine (validateVizEquivalenceRules): error-severity rules BLOCK (status:'error' with per-rule OODS-<rule.id> codes in `errors`), warn-severity failures surface in `warnings` as OODS-<rule.id>. Default builder output is conformant-BY-CONSTRUCTION , so generated specs pass; set false to opt out for agent-supplied non-conformant specs. Scoped to the cartesian path (the ECharts-primary scaffold has empty data and would spuriously fail data-equivalence rules).","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows/datasetRef with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link MUST carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. Carries INLINE geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination ARCS for flow_map. Geometry is supplied INLINE — it is never fetched over the network. NOTE: geo specs are NOT self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the DESTINATION latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the DESTINATION longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the ORIGIN latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the ORIGIN longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"STRUCTURED (typed, NOT free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it INSTEAD of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive ENCODING, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick, and an optional governed `measureRef` lights the governed-measure narrative overlay (only when output.includeA11y=true). Requires `rows` (or a `datasetRef`).","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (NOT a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 TABULAR marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link MUST reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' MUST match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, datasetRef, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used INSTEAD of rows/datasetRef + x/y encodings. Nodes plus value-weighted links; every link MUST carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Field/key-presence STRICT switch. When true, a referenced data key that does not resolve is surfaced in `warnings` instead of a silent confident-wrong result: (m05) an explicit tabular chart whose encoding references a field ABSENT from every (non-empty) row → OODS-V131; (m06) a choropleth corridor whose join key has NO matching map feature → OODS-V134 (per unmatched corridor). DEFAULT false keeps today's behavior byte-identical (the geo silent-drop preserved). The dashboard.render strict check (its own `strictFields`) escalates V131 to an error panel via `onPanelError`.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}after
{"$defs":{"colorEncodingBinding":{"description":"A color-channel encoding binding: like encodingBinding, plus an optional explicit `range` (hex colors) that overrides the baked OODS categorical palette on a nominal/ordinal color scale. `range` is only valid on the color channel.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"field":{"minLength":1,"type":"string"},"range":{"description":"Explicit hex colors for a nominal/ordinal color scale. Overrides the baked OODS categorical palette so an agent can supply its own scale (e.g. a 2-color presence scale). Applied in array order to the distinct series; a shorter range recycles (Vega domain[i]->range[i] mod len). Cartesian color only.","items":{"pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$","type":"string"},"minItems":2,"type":"array"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"encodingBinding":{"description":"An encoding binding: either a bare field-name string, or an object with the field plus optional aggregate/scale/timeUnit/sort/title.","oneOf":[{"minLength":1,"type":"string"},{"additionalProperties":false,"properties":{"aggregate":{"enum":["sum","count","average","median","min","max","distinct"],"type":"string"},"currency":{"description":"ISO 4217 code of the amounts this channel encodes, for example EUR. The labels print its en-US symbol where the format has \"$\" (EUR €, GBP £); without a format they read \"$,f\" ($12,000). One currency per chart.","pattern":"^[A-Za-z]{3}$","type":"string"},"field":{"minLength":1,"type":"string"},"format":{"description":"Label format of this channel's axis (x, y) or legend: a d3-format specifier such as \"$,f\" or \",.0f\" (d3-time-format for a temporal field). \"$\" prints the currency symbol: the currency's, else $. Without a precision, labels take the precision of the tick step, so neighbouring ticks never print the same text. Carried in the normalized spec, so artifact.certify replays it.","maxLength":64,"minLength":1,"type":"string"},"scale":{"enum":["linear","temporal","log","sqrt","band","point","diverging"],"type":"string"},"sort":{"oneOf":[{"enum":["none","ascending","descending"],"type":"string"},{"additionalProperties":false,"properties":{"field":{"type":"string"},"order":{"enum":["ascending","descending"],"type":"string"}},"required":["field","order"],"type":"object"}]},"timeUnit":{"enum":["year","quarter","month","week","day","hour","minute","second"],"type":"string"},"title":{"type":"string"},"type":{"description":"Force the Vega-Lite/ECharts field type, overriding the engine's data-aware inference. Overrides the inferred field type.","enum":["quantitative","temporal","ordinal","nominal"],"type":"string"}},"required":["field"],"type":"object"}]},"hierarchyNode":{"additionalProperties":true,"description":"A nested-hierarchy node: a name, an optional numeric value, and optional children (recursive). Extra fields are preserved for tooltips.","properties":{"children":{"items":{"$ref":"#/$defs/hierarchyNode"},"type":"array"},"name":{"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"}},"$id":"https://designlab.local/schemas/viz.render.input.json","$schema":"https://json-schema.org/draft/2020-12/schema","additionalProperties":false,"description":"Render a real, data-bound visualization. Supply a registered pattern identity to preserve its source data and presentation, chartType + encodings for explicit mode, or rows for suggest or structured-intent mode. Retired patterns are not offered; structurally unsupported patterns return OODS-V167; pattern conflicts with explicit data, intent, or source identity/presentation overrides return OODS-V166. Brand, theme and output controls remain available.","properties":{"a11yEquivalence":{"default":true,"description":"A11y equivalence CERTIFY-AT-EMISSION switch. DEFAULT ON. The cartesian (Vega-Lite) emission is checked against the accessible-equivalence engine (validateVizEquivalenceRules): error-severity rules BLOCK (status:'error' with per-rule OODS-<rule.id> codes in `errors`), warn-severity failures surface in `warnings` as OODS-<rule.id>. Default builder output is conformant-BY-CONSTRUCTION , so generated specs pass; set false to opt out for agent-supplied non-conformant specs. Scoped to the cartesian path (the ECharts-primary scaffold has empty data and would spuriously fail data-equivalence rules).","type":"boolean"},"brand":{"default":"A","enum":["A","B"],"type":"string"},"chartType":{"description":"Chart type. The tabular marks (bar->MarkBar, line->MarkLine, area->MarkArea, scatter->MarkPoint, heatmap->MarkRect) bind inline rows with x/y encodings. The hierarchy/flow/network/geo charts are explicit-only and return an ECharts option as the primary spec (no Vega-Lite equivalent): 'treemap' and 'sunburst' take the 'hierarchy' data branch; 'sankey' takes the 'sankey' data branch (nodes + value-weighted links); 'force_graph' takes the 'network' data branch (nodes + links); 'choropleth', 'bubble_map', and 'flow_map' take the 'geo' data branch (inline geometry + per-type encoding — flow_map draws origin→destination arcs); 'chord' takes the 'chord' data branch (sankey-shaped nodes + value-weighted links — a ring of category arcs joined by ribbons whose width is the value). Omit chartType to enter suggest mode (the recommender chooses a tabular type from the inferred field profiles).","enum":["bar","line","area","scatter","heatmap","treemap","sunburst","sankey","force_graph","choropleth","bubble_map","flow_map","chord"],"type":"string"},"chord":{"additionalProperties":false,"description":"Chord data for chartType 'chord' (explicit-only) — used INSTEAD of rows + x/y encodings. A native ECharts ribbon diagram: a ring of category arcs connected by weighted ribbons. Sankey-shaped — nodes plus value-weighted links; every link MUST carry a numeric 'value' (the ribbon width IS the flow magnitude) and reference existing node names — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed, value-weighted ribbons between ring arcs (matched to arcs by name). Directed: source→target and target→source are distinct ribbons (a reciprocal pair is valid data). Each (source, target) pair should be unique — a duplicate directed link double-counts the ribbon and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Ring arcs. Each carries a unique 'name'.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"description":{"description":"Optional override for the synthesized accessibility description. When omitted, a non-empty description is generated from the encodings.","type":"string"},"encodings":{"additionalProperties":false,"description":"Channel -> field bindings. Required, with at least x and y, when chartType is supplied (explicit mode).","properties":{"color":{"$ref":"#/$defs/colorEncodingBinding"},"detail":{"$ref":"#/$defs/encodingBinding"},"shape":{"$ref":"#/$defs/encodingBinding"},"size":{"$ref":"#/$defs/encodingBinding"},"x":{"$ref":"#/$defs/encodingBinding"},"y":{"$ref":"#/$defs/encodingBinding"}},"type":"object"},"geo":{"additionalProperties":false,"description":"Geo data for chartType 'choropleth', 'bubble_map', or 'flow_map' (explicit-only) — used INSTEAD of rows + x/y encodings. Carries INLINE geometry (a GeoJSON FeatureCollection in 'geojson', or a TopoJSON Topology in 'topojson' + 'topoObjectName'), an optional 'join' that merges tabular 'rows' into features by key, and the per-type encoding: 'valueField' colours regions for choropleth; 'longitudeField'/'latitudeField' (+ optional 'sizeField'/'colorField') place points for bubble_map; 'originLongitudeField'/'originLatitudeField'/'destinationLongitudeField'/'destinationLatitudeField' (+ optional 'strengthField'/'curvature') draw origin→destination ARCS for flow_map. Geometry is supplied INLINE — it is never fetched over the network. NOTE: geo specs are NOT self-contained (unlike treemap/sankey): the resolved FeatureCollection rides back on echartsSpec.__registration and the client re-registers the map by name before rendering. Geometry payloads can be large (a world atlas is ~100KB) — prefer a pre-simplified TopoJSON.","properties":{"colorField":{"description":"Bubble map: optional row field driving bubble colour.","minLength":1,"type":"string"},"colorScale":{"description":"Optional colour scale (defaults to a continuous linear ramp). 'ordinal' paints discrete per-category colours; 'diverging' ramps two hues about a neutral midpoint (zero).","enum":["linear","quantize","quantile","threshold","ordinal","diverging"],"type":"string"},"curvature":{"description":"Flow map: optional arc curveness (0 = straight, ~0.3 default). Bends each origin→destination line into an arc.","maximum":1,"minimum":0,"type":"number"},"destinationLatitudeField":{"description":"Flow map: the row field holding the DESTINATION latitude. Required for flow_map.","minLength":1,"type":"string"},"destinationLongitudeField":{"description":"Flow map: the row field holding the DESTINATION longitude. Required for flow_map.","minLength":1,"type":"string"},"geojson":{"additionalProperties":true,"description":"Inline GeoJSON FeatureCollection (type:'FeatureCollection', features:[...]). Required for choropleth (the regions); optional base map for bubble_map.","type":"object"},"join":{"additionalProperties":false,"description":"Choropleth join: merge each row into the feature whose 'featureProperty' equals the row's 'dataKey' value.","properties":{"dataKey":{"description":"Key in each tabular row.","minLength":1,"type":"string"},"featureProperty":{"description":"Matching property name in each feature's properties.","minLength":1,"type":"string"}},"required":["dataKey","featureProperty"],"type":"object"},"latitudeField":{"description":"Bubble map: the row field holding latitude. Required for bubble_map.","minLength":1,"type":"string"},"longitudeField":{"description":"Bubble map: the row field holding longitude. Required for bubble_map.","minLength":1,"type":"string"},"originLatitudeField":{"description":"Flow map: the row field holding the ORIGIN latitude. Required for flow_map.","minLength":1,"type":"string"},"originLongitudeField":{"description":"Flow map: the row field holding the ORIGIN longitude. Required for flow_map.","minLength":1,"type":"string"},"rows":{"description":"Tabular records: for choropleth, the values joined into features (paired with 'join'); for bubble_map, the points to plot.","items":{"additionalProperties":true,"type":"object"},"maxItems":5000,"type":"array"},"sizeField":{"description":"Bubble map: optional row field driving bubble size.","minLength":1,"type":"string"},"strengthField":{"description":"Flow map: optional numeric row field whose magnitude drives each arc's line width (via a continuous visualMap).","minLength":1,"type":"string"},"topoObjectName":{"description":"Which TopoJSON object to extract (defaults to the sole object when there is exactly one).","minLength":1,"type":"string"},"topojson":{"additionalProperties":true,"description":"Inline TopoJSON Topology (type:'Topology'); converted to a GeoJSON FeatureCollection. Set 'topoObjectName' when the topology holds more than one object.","type":"object"},"valueField":{"description":"Choropleth: the numeric field — in feature properties, or merged in via 'join' — whose value colours each region. Required for choropleth.","minLength":1,"type":"string"}},"type":"object"},"hierarchy":{"description":"Hierarchy data for chartType 'treemap' or 'sunburst' (explicit-only) — used INSTEAD of rows + x/y encodings. A discriminated union on 'type': 'adjacency_list' (flat nodes linked by parentId; a node whose parent is missing becomes its own root) or 'nested' (a single root node with children).","oneOf":[{"additionalProperties":false,"properties":{"data":{"description":"Flat node list. Each node carries id, parentId (null for roots), and a numeric value.","items":{"additionalProperties":true,"properties":{"id":{"minLength":1,"type":"string"},"name":{"type":"string"},"parentId":{"type":["string","null"]},"value":{"type":"number"}},"required":["id","parentId","value"],"type":"object"},"minItems":1,"type":"array"},"type":{"const":"adjacency_list"}},"required":["type","data"],"type":"object"},{"additionalProperties":false,"properties":{"data":{"$ref":"#/$defs/hierarchyNode"},"type":{"const":"nested"}},"required":["type","data"],"type":"object"}]},"id":{"description":"Optional stable identifier for the produced spec.","type":"string"},"intent":{"additionalProperties":false,"description":"STRUCTURED (typed, NOT free-text) visualization intent — the deterministic half of the NL→viz hand-off. Supply it INSTEAD of chartType/encodings (mutually exclusive with chartType): the named measures/dimensions drive ENCODING, `goal` + the data drive the recommender's chartType pick, an optional `chartFamily` post-filters that pick. Requires `rows`.","properties":{"chartFamily":{"description":"Optional preferred chart family. Post-filters the recommender ranking (NOT a scorer term) to this family, flagged lowConfidence when it was not the recommender's top pick. Constrained to the 5 TABULAR marks — the 8 explicit-only types are not recommender-rankable.","enum":["bar","line","area","scatter","heatmap"],"type":"string"},"dimensions":{"description":"Named dimension fields (the breakdowns/axes); may be empty (e.g. a two-measure scatter). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"type":"array"},"goal":{"description":"The analytical goal that steers the recommender (the live 7-value goal vocabulary).","enum":["comparison","trend","composition","part-to-whole","relationship","intensity","distribution"],"type":"string"},"measures":{"description":"Named measure fields (the metrics to plot). Each name MUST exist among the data rows' fields. `type` is RESERVED in v0.1 (field types infer from the data).","items":{"additionalProperties":false,"properties":{"name":{"minLength":1,"type":"string"},"type":{"enum":["quantitative","temporal","nominal","ordinal"],"type":"string"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["goal","measures","dimensions"],"type":"object"},"name":{"description":"Optional human-friendly chart title.","type":"string"},"network":{"additionalProperties":false,"description":"Network data for chartType 'force_graph' (explicit-only) — used INSTEAD of rows + x/y encodings. Nodes (each with a unique 'id'; an optional 'group' drives category colour) and directed links (optional numeric 'value'). Every link MUST reference existing node ids — a link naming a node absent from 'nodes' fails loud (OODS-V147).","properties":{"links":{"description":"Directed edges between nodes (an empty array is allowed for an all-isolated-nodes graph). Each 'source'/'target' MUST match a node 'id' (a dangling ref fails loud, OODS-V147). Directed: source→target and target→source are distinct edges. Each (source, target) pair should be unique — a duplicate directed edge double-counts and is flagged with a warning (OODS-V148).","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target"],"type":"object"},"type":"array"},"nodes":{"description":"Graph nodes. Each carries a unique 'id'; optional 'group' (category) and 'value' (sizing).","items":{"additionalProperties":true,"properties":{"group":{"type":"string"},"id":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["id"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"opacity":{"description":"Optional constant mark opacity for the five Cartesian chart families. Preserved in normalized mark options and applied to both Vega-Lite and ECharts pixels. Omission preserves renderer defaults. Unsupported for hierarchy, network and geographic chart families.","maximum":1,"minimum":0,"type":"number"},"output":{"additionalProperties":false,"properties":{"height":{"maximum":2000,"minimum":100,"type":"integer"},"includeA11y":{"const":true},"includeNormalizedSpec":{"const":true},"svg":{"const":true},"width":{"maximum":2000,"minimum":100,"type":"integer"}},"required":[],"type":"object"},"pattern":{"description":"Exact versioned pattern source identity. Renderable patterns preserve source rows, identity, presentation and accessibility metadata. Retired identities are not offered (their reasons are in the viz taxonomy). Structurally unsupported scenes return OODS-V167. Static SVG shows the default selection state (OODS-V175). Cannot be combined with chartType, encodings, rows, intent, hierarchy, sankey, chord, network, geo, id, name, description or opacity (OODS-V166).","enum":["pattern:viz:bubble-distribution","pattern:viz:correlation-matrix","pattern:viz:correlation-scatter","pattern:viz:detail-overview-bar","pattern:viz:diverging-bar","pattern:viz:drilldown-stacked-bar","pattern:viz:facet-small-multiples-line","pattern:viz:facet-target-band","pattern:viz:focus-context-line","pattern:viz:grouped-bar","pattern:viz:histogram","pattern:viz:layered-line-area","pattern:viz:multi-series-line","pattern:viz:running-total-area","pattern:viz:simple-bar","pattern:viz:sparkline-grid","pattern:viz:stacked-100-bar","pattern:viz:stacked-area-projection","pattern:viz:stacked-bar","pattern:viz:target-band-line","pattern:viz:time-grid-heatmap","pattern:viz:waterfall"],"type":"string"},"rows":{"description":"Inline data rows — the primary data path. Bounded: a few hundred rows is the sweet spot. Each row is a flat object mapping field name to value.","items":{"additionalProperties":true,"type":"object"},"maxItems":500,"minItems":1,"type":"array"},"sankey":{"additionalProperties":false,"description":"Flow data for chartType 'sankey' (explicit-only) — used INSTEAD of rows + x/y encodings. Nodes plus value-weighted links; every link MUST carry a numeric 'value' (the link width IS the flow magnitude) and reference existing node names.","properties":{"links":{"description":"Directed, value-weighted flows between nodes. Each (source, target) pair should be unique — a duplicate directed flow double-counts the link width. (Uniqueness is advisory for sankey; it is not warning-enforced.)","items":{"additionalProperties":true,"properties":{"source":{"minLength":1,"type":"string"},"target":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["source","target","value"],"type":"object"},"minItems":1,"type":"array"},"nodes":{"description":"Flow nodes. Each carries a unique 'name'; an optional numeric 'value' overrides the computed throughput.","items":{"additionalProperties":true,"properties":{"name":{"minLength":1,"type":"string"},"value":{"type":"number"}},"required":["name"],"type":"object"},"minItems":1,"type":"array"}},"required":["nodes","links"],"type":"object"},"strictFields":{"default":false,"description":"Field/key-presence STRICT switch. When true, a referenced data key that does not resolve is surfaced in `warnings` instead of a silent confident-wrong result: (m05) an explicit tabular chart whose encoding references a field ABSENT from every (non-empty) row → OODS-V131; (m06) a choropleth corridor whose join key has NO matching map feature → OODS-V134 (per unmatched corridor). DEFAULT false keeps today's behavior byte-identical (the geo silent-drop preserved). The dashboard.render strict check (its own `strictFields`) escalates V131 to an error panel via `onPanelError`.","type":"boolean"},"theme":{"default":"light","enum":["light","dark","hc"],"type":"string"}},"title":"Viz render input","type":"object"}before
—after
List ComponentsReadList thecomponentpinnedcatalogregistry’swithcomponents, a page at a time. category, trait and context filter thepackage’slist (each reply’s availableCategories names the categories); status filters by the legacy static-HTML status only. detail sets each entry’s size: brief (name, categories andpagination.one readiness label; the default with no filter), summary (adds tags, contexts, regions and traits) or full (adds the evidence; the default with a filter). page and pageSize walk through totalCount, up to 200 a page, and hasMore says whether another page follows. Use it to choose components; use structured_data_fetch with dataset components instead for the whole export in one reply, and object_registry for objects. Read-only.
before
—after
Look Up Recorded ScreenLook upFind apre-builtscreen OODS Foundry generated at the pinned version: objectscreenandincontext pick one of the recorded object screens, and framework its React orVue.VueReturnsapp.itsReturnshostedthe URL on oods-foundry.com where that built app runs, its recorded content hash, the brand andexacttheme it was generated in, and the three localreproductioncallscalls.that reproduce it (brand_create, design_compose, code_generate). Nothing is composed or generated here; for a live preview of your own composition, call design_preview over local stdio. Use object_registry show instead to read the definition behind a screen.
before
—after
Snapshot RegistryRead the whole pinned registrysnapshot.in one reply: every active object (fields, semantics, tokens, traits) and every trait’s full definition, keyed by name, with the recorded component mappings (none on this hosted process), a canonical etag and generatedAt. registry names the live source, the loaded names and any loader issues; includeInternal adds OODS Foundry’s internal objects, which registry.hiddenInternal counts otherwise. Use object_registry show instead for one object’s composed definition with its view extensions, and catalog_list for components. Read-only, with no side effects: it writes nothing and changes no state.
before
—after
Read Tool SchemaReadathetool’sfullshippedJSON Schema of any OODS Foundry tool at the pinned version, as the package ships it: name is any of its tools, local-only ones included, and kind is input (the default) oroutputoutput. Returns the schema,withitssourcefileURLin the package, that file’s SHA-256 andfileitshash.URLLocalonschemasthisdescribesite.theUsefullitpackage;before calling a tool over local stdio, or to learn what a tool returns: these hosted tools declare no output schema, and tools/listdescribesherethisshows narrowerhostedinputssurface.than local stdio accepts.
⟨11 unchanged words⟩ ,"name":{"enum":["tokens_build","structuredData_fetchstructured_data_fetch","brand_apply","brand_intakebrand_create","catalog_list","code_generate","design_compose","design_preview","pipelinepipeline_run","healthhealth_check","registry_snapshot","viz_render","dashboard_render","artifact_certify","fidelity_preview","mapcomponent_map","schemaschema_store","objectobject_registry","replschema_render","a11y_scan"],"type":"string"}} ⟨4 unchanged words⟩
before
—after
Render ChartDraw a chartthroughwiththisthesite’spinned OODS Foundry and certify it, in one call. Give inline rows with chartType and encodings; a pattern id to draw a catalog chartroute.withReturnsits own rows; an intent (goal, measures, dimensions) instead of encodings; or rows without chartType to have one recommended. brand A or B and theme light, dark or hc set therealcolours. The reply holds viz_render’s result (the SVG,hashes,contentHashaccessibleandoutputsvgHash,normalizedthe Vega-Lite or ECharts spec, normalizedSpec, andcertification.an accessible table and narrative) and artifact_certify’s verdict on that normalizedSpec in the same scope: conformant and the four pillars. Use it for any chart; artifact_certify returns the same reply. Inline dataonly;onlybrands(noA/BdatasetRefandorlight/dark/hc.measureRef), up to 500 rows; the same input returns the same bytes.
Check Health — Check the OODS Foundry process behind these tools: its status, package version and uptime, registry counts (components, objects, traits), the built brands, themes and token scopes, and the retained proof summaries, each naming the release it measured. Use it first, to learn the pinned version; use catalog_list, object_registry or registry_snapshot instead to read what the counts describe. includeChangelog adds the DSL changelog, and sinceVersion, given with it, keeps only the entries after that version. Read-only and never cached: uptime and latency are this call’s. Host folder paths are omit…
Read Object Registry — Read the pinned registry’s objects. action list returns the objects in use, business objects first, each with its source, traits and field count; domain, trait and maturity filter it, and includeInternal adds OODS Foundry’s internal objects, which hiddenInternal counts otherwise. action show, with name, returns one object’s composed definition: traits, fields and their semantics, view extensions by context, tokens and relationships; context narrows the view extensions to one context. Use registry_snapshot instead for every object and trait in one reply, and design_preview to see a generated s…
Fetch Structured Data — Fetch one registry dataset as a single export: dataset components (the live registry’s components, objects and traits), tokens or manifest. The reply carries the export’s version date, an etag, sizeBytes and the payload. listVersions returns the dated exports instead of a payload, and version picks one of them (the nearest earlier date, with a warning, when that date has none). Pass a previous etag as ifNoneMatch to get matched: true and no payload when nothing changed; includePayload: false omits the payload anyway. includeInternal applies to components only. Use catalog_list instead to filt…
Read the pinned OODS Foundry process health. Host folder paths are omitted.
List or show object definitions. The hosted surface accepts these read actions only.
Read components, tokens or manifest registry datasets, including their available versions.