HyperPBI dashboard authoring skill
Generate or repair declarative HyperPBI dashboard specifications for a Power BI custom visual. Dashboard schema version 2.0 is the only supported authoring and rendering contract. Reject schema 1.0 and missing versions.
Output contract
Return exactly the output requested by the job and nothing else. Use valid JSON with no Markdown fence, prose, comment, trailing comma, JSON Patch, JavaScript, function, callback, event-handler string, credential, or invented field.
- Create and improve jobs return one complete specification object.
- Add-section jobs return the requested validated section package with its insertion target.
- Redesign-section jobs return one replacement component/section using the selected stable ID.
- Repair jobs return one complete corrected specification object.
For normal improvement and repair jobs, never return JSON Patch. Return version "2.0" and preserve stable component IDs, valid unrelated content, interactions, datasets, definitions, app state, and styling. Change only what the request or supplied diagnostics require.
Strict 2.0 root
The minimal root is:
{"version":"2.0","components":[]}
Allowed root properties are version, title, theme, layout, state, app, leftPanel, rightPanel, toolbar, components, css, styles, calculations, data, and definitions. Under data, only sources and datasets are allowed. Version 2.0 rejects unknown root and component properties.
Every component requires type and a globally unique stable id matching ^[A-Za-z][A-Za-z0-9_-]{0,99}$. IDs are behavior contracts: preserve them when the same component remains, and target only IDs that exist.
Fields and the Field Manifest
Use only aliases supplied in the current Field Manifest. An alias is an AI-facing identifier; preparation resolves it to a canonical runtime key. Display names, source table/column names, and Power BI query names are metadata, not interchangeable authoring identifiers.
Respect field origin:
- A true model measure has model-measure origin and cannot be a basic model-column filter target.
- A query aggregation such as
Sum(Sales.Amount)is an implicit aggregation over the model columnSales.Amount, not a model measure. - Model columns with source table/column metadata can support external filters.
- Dataset-derived fields and dataset metrics are local results and cannot directly filter the semantic model.
- Renamed model columns and group-by fields retain source metadata when available.
- Exact external selection requires Power BI identities or source-row lineage; it is different from external filtering.
Never invent an alias, normalized key, model measure, aggregation, or business rule.
Logical datasets
data.sources may declare read-only miniup.table, miniup.function, and web-only rest.get sources. A component may bind directly to a source name. data.datasets definitions require source, which may be powerbi, a declared source, or another named dataset. Allowed dataset properties are source, filter, derive, rename, select, groupBy, metrics, distinct, sort, and limit.
Runtime and static-schema order is: resolve source; filter; derive; rename; select; groupBy/metrics; distinct; sort; limit. Metric operations are sum, avg, min, max, count, distinctCount, and first. Derive expressions use the safe calculation DSL. Remote schemas are dynamic until a response arrives, so never invent remote fields; use only names explicitly supplied by the user/current specification or a known response contract. No SQL, joins, executable JavaScript, request mutations, custom headers, embedded credentials, or arbitrary untrusted hosts.
A component omitting dataset uses powerbi; otherwise it sees only the selected source/dataset output fields. Power BI external selection/filtering applies only to datasets rooted in powerbi. Remote rows support HyperPBI internal interaction but never gain Power BI identity. Source cycles, unknown sources, collisions, and missing known fields are errors.
Reusable definitions and application patterns
Root definitions are reusable component fragments. A component instance uses use; objects merge recursively, arrays are replaced, the definition's ID is removed, and every instance supplies its own stable ID. Cycles and unknown definitions are errors.
Available patterns are kpi-row, trend-and-breakdown, record-explorer, and map-and-details. A pattern is {"type":"pattern","pattern":"...","id":"stable-id"} plus the pattern's required fields. Patterns expand before validation; generated child IDs derive from the pattern ID. Use a pattern only when its structure matches the user's intent.
Components
Use the canonical component catalog included with the prompt. It contains 81 types in 12 categories, including first-class semantic charts, native table and matrix, map, declarative svg, sanitized svgMarkup, and advancedChart. Use only properties listed for that type.
Prefer first-class components over custom markup: card over a simulated card, listGroup over a hand-built list, dataGrid/detailPanel over manual detail HTML, semantic charts over advancedChart, and svg over svgMarkup.
Exclude deprecated types. Include experimental types only when explicitly requested and beta types only when explicitly requested or advanced authoring is selected. Stable requires renderer, strict schema, applicable field metadata, Inspector metadata, valid example, responsive/empty-state behavior, accessibility guidance, focused tests, and documentation evidence.
Shared 2.0 properties include type, id, dataset, title, subtitle, span, className, hidden, props, style, css, slots, data, visibility, interactions, interaction, ariaLabel, icon, variant, size, disabled, tooltip, and uiAction. An interaction object is not required on every component.
Application shell and overlays
Configure the application shell at root app, never schema.app. It can define brand, navbar, sidebar, page header, footer, density, container, and layout. Use a permanent shell only when the visual size supports it; prefer offcanvas for narrow layouts.
Overlay components require unique IDs. Target existing IDs with openOverlay, closeOverlay, or toggleOverlay. Use dropdown for commands, popover for contextual content, offcanvas for details/filters, and modal for focused blocking work.
Responsive layout and sizing
Author mobile-first container-relative overrides under responsive.xs|sm|md|lg|xl. Each rule may set span, order, visible or hidden, direction, columns, or stack. Use heightMode: "fill" only when a parent establishes bounded height; it propagates through nested grid/flex/split containers, cards, tabs, charts, maps, and virtual tables. Use heightMode: "aspectRatio" with a positive aspectRatio for self-sized analytical panels and retain existing fixed height properties for compatibility.
A resizable split accepts one positive sizes value per child, optional aligned minSizes and maxSizes, resizable: true, persist: "none"|"session"|"local", and optional storageKey. Sizes are percentages, normalized to 100, constrained during pointer/keyboard resizing, and safely ignored from storage when incompatible. Stack a split at narrow breakpoints and restore row direction later for application-style mobile layouts.
Targeted change packages
Use kind: "hyperpbi-change" and only the properties permitted by the operation. Its envelope protocol version is "1.0", which is distinct from the enclosed dashboard schema version. replace requires a matching targetId and component.id; insertBefore and insertAfter target a component in an ordered array; appendChild requires a descriptor-compatible relative containerPath such as children, footer, tabs/1/children, or items/0/children; appendRoot uses exactly components, toolbar, leftPanel, or rightPanel; remove carries only targetId. Never use absolute or parent paths. Validate the complete resulting dashboard; a successful result becomes the working JSON and preview together.
Three interaction systems
uiActionchanges interface state. Types:clearFilters,setTab,setState,toggleState,toggleSidebar,openOverlay,closeOverlay,toggleOverlay,setStep,nextStep,previousStep,showToast,dismissToast,scrollTo, andrefresh(safe no-op).- Universal
interactioncontrols data behavior: triggerauto|click|change; internal modenone|highlight|filter; scopeself|others|all; external modenone|auto|selection|filter; operators=|!=|>|>=|<|<=|contains|in|between; selection modereplace|toggle|add. interactionsmaps safe component events to allowlisted actions such asselectRow,selectWhere,clearSelection,setFilter,clearFilter,setState,toggleState,openTab,toggleCollapse,drillToDetail,highlight, andclearHighlight.
These systems are independent and can coexist. externalMode: "auto" resolves to filter for controls and selection for data points/custom content. External filter mode requires a supplied real model-column alias. Do not claim a dataset metric or derived field can directly filter Power BI.
Use interaction.target or interaction.targets to restrict linked internal filtering/highlighting to existing component IDs; omission preserves report-wide behavior.
Charts additionally accept events.zoom, events.rangeSelect, and events.brush. Each event has enabled, optional event-specific interaction, optional targets, and optional field. Zoom keeps its ECharts data window across rerenders; range and brush selections resolve adapter points to deduplicated source-row lineage. Use drill.levels for real hierarchy navigation: define at least two already-declared dataset views and bindings, then put parentField on each child level. trigger is click|doubleClick; breadcrumbs navigate backward. Never invent an on-demand query or mutate a dataset during drill.
Native tables accept virtualization: {enabled, threshold, rowHeight, overscan} and export: {enabled, formats, scope, fileName}. Threshold is 1–5,000, row height is 22–80 pixels, and overscan is bounded. Virtualization mounts only the visible window but search, sort, selection, and export operate on the full prepared result; explicitly disabling it retains a 5,000-row DOM guard. Export formats are csv|xlsx; scope is filtered|selected|selectedOrFiltered. Both are local, neutralize spreadsheet-formula prefixes, and remain subject to the visual-format maximum-row limit.
The universal trigger vocabulary is component-wide, but map layers currently implement click only. A map layer using auto or change is invalid and must be repaired before rendering.
SVG and svgMarkup
Use svg for governed diagrams, gauges, pictorial marks, process flows, and schematics—not standard analytical charts. Supported structured elements are g, path, rect, circle, ellipse, line, polyline, polygon, text, tspan, defs, linearGradient, radialGradient, stop, clipPath, mask, marker, title, and desc.
Values can be literal, bound, templated, scaled, mapped, conditional, or state-based. Data contexts are aggregate, selectedRow, and first. Repeats are bounded and may select a dataset. Animation presets are fade-in, slide-in, scale-in, pulse, float, swim, rotate, draw-path, progress-fill, follow-progress, flow-dash, blink-status, bounce, and shimmer; triggers are auto, hover, focus, selected, dataChange, state, and none. Include an accessible label and respect reduced motion.
Use svgMarkup only when structured SVG is insufficient. It is a sanitized single SVG document: no script, handlers, style element/attribute, external URL, foreignObject, image, use, link, animation element, or field-injected path data.
Maps
All Power BI fields arrive through the single Values role. Declare explicit layers[]; select a logical layer.dataset when needed; and configure each Power BI layer's source.bindings for geometry, latitude/longitude, X/Y, address, grouping, color, size, tooltip, and details. Never depend on a map-specific Power BI field bucket. A layer omitting dataset inherits the map dataset, then powerbi. Map center order is [latitude, longitude].
Power BI supplies one flattened visual data view. Fields may originate from related model tables, but row grain and combinations are determined by the visual query and semantic-model relationships. Logical datasets only transform that received data; they do not query model tables independently or create relationships. Reference-only ArcGIS, GeoJSON, and XYZ maps require no Values fields; never add unrelated model fields merely to activate an external layer. External sources are allowed HTTPS geoJson and xyz sources or public HTTPS arcgisFeature, arcgisTile, and arcgisDynamic services subject to the installed Maps package and host policy. Never invent a URL, layer ID, field, host, token, or credential. Do not promise secured services, feature editing, 3D, geoprocessing, relationships, tracing, or complete Esri builder parity. Heatmap is implemented as a real weighted canvas raster; density grid remains experimental, fill patterns remain partial, and exact service-scale visibility and mounted-view persistence retain their documented limitations.
Map Studio and the preview share prepared calculations/configuration/datasets/lineage. Map attributes use exact powerbi|service|joined sources, and service queries include only service fields. view.fitPadding is a ratio from 0 through 0.5, normally 0.08. Use the declared renderer and safe symbol/icon schema; never emit marker JavaScript or unrestricted HTML. Feature click, interactive legends, rectangle/lasso/circle tools, Select visible, Invert, quick filters, external Power BI state, and linked components share canonical feature keys and eligible Power BI lineage. Heat pixels and density summaries are not selectable; set heatmap interactivePoints: true when source-record hit testing is required. Metadata fetch, bounded join preview, interaction compatibility, and live-view bookmark capture are explicit Studio workflows rather than persisted service metadata.
Map Studio validates every draft against the exact current Runtime Config supplied by its owner and never fabricates a default. Service inspection performs one root request, distinguishes groups, selectable spatial layers, and tables, and lazily fetches selected-layer metadata with successful-result caching. Join behavior is cardinality-aware: oneToOne rejects duplicates on either side, manyToOne permits repeated Power BI keys but requires unique service keys, and unmatched/aggregation diagnostics follow the declared policies. Numeric aggregations ignore blanks and non-finite or nonnumeric values; an empty valid set yields null. Class breaks cap the requested count to the color ramp and distinct sample values, collapse repeated quantile boundaries, and keep the final upper bound inclusive. External tile and dynamic layers are reused when their stable definition is unchanged and replaced or removed when meaningful definitions or access policy change. Diagnostics use canonical JSON Pointer paths and are scoped to the selected layer.
Repair behavior
Use supplied structured diagnostics as the authority. The version must be present and exactly "2.0"; preparation never infers it. HyperPBI's optional authoring repair pass handles only unambiguous cases such as missing stable component IDs, the known property typos meausre, catgory, componets, and aggregration, and bounded numeric strings. AI response import uses strict validation and performs no repairs. It does not repair comments, smart quotes, truncated JSON, unknown business fields, ambiguous aliases, unknown component types, unsafe content, or speculative intent.
Security
Never emit user JavaScript, eval, executable functions, callbacks, inline handlers, scripts, iframes, arbitrary URLs, CSS imports, credentials, AI keys, SQL, joins, request mutations, or custom request headers. Declared read-only remote sources are allowed only under data.sources and must follow the host policy. HTML is sanitized. CSS is parsed, allowlisted, and scoped. ECharts options are recursively sanitized and semantic chart options cannot replace generated data bindings. SVG is allowlisted, namespaced, sanitized, and limited. ArcGIS access is HTTPS and host-policy controlled.
Schema version boundary
Dashboard schema 2.0 is the only active contract. Dashboard schema 1.0 is never migrated during visual loading, Edit Mode, AI import, preview, save, or rendering. Developers may convert a legacy JSON file explicitly with npm run schema:migrate-v1 -- input.json output.json; the temporary converter is not part of the PBIVIZ runtime. The Power BI package version and Runtime Config version are independent version numbers.