@miragon/mcp-toolkit-ui 2.6.0 → 2.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +14 -5
- package/dist/app/adapt-data-widget.d.ts +1 -22
- package/dist/app/adapt-data-widget.d.ts.map +1 -1
- package/dist/app/adapt-data-widget.js +1 -35
- package/dist/app/adapt-data-widget.js.map +1 -1
- package/dist/app/builder/BuilderBanners.d.ts +7 -2
- package/dist/app/builder/BuilderBanners.d.ts.map +1 -1
- package/dist/app/builder/BuilderBanners.js +8 -3
- package/dist/app/builder/BuilderBanners.js.map +1 -1
- package/dist/app/builder/CanvasRow.d.ts +4 -2
- package/dist/app/builder/CanvasRow.d.ts.map +1 -1
- package/dist/app/builder/CanvasRow.js +29 -17
- package/dist/app/builder/CanvasRow.js.map +1 -1
- package/dist/app/builder/CatalogueSheet.d.ts.map +1 -1
- package/dist/app/builder/CatalogueSheet.js +14 -6
- package/dist/app/builder/CatalogueSheet.js.map +1 -1
- package/dist/app/builder/CellPropsSheet.d.ts +7 -3
- package/dist/app/builder/CellPropsSheet.d.ts.map +1 -1
- package/dist/app/builder/CellPropsSheet.js +10 -3
- package/dist/app/builder/CellPropsSheet.js.map +1 -1
- package/dist/app/builder/DiscardDialog.d.ts +18 -0
- package/dist/app/builder/DiscardDialog.d.ts.map +1 -0
- package/dist/app/builder/DiscardDialog.js +18 -0
- package/dist/app/builder/DiscardDialog.js.map +1 -0
- package/dist/app/builder/EmptyHint.d.ts +4 -0
- package/dist/app/builder/EmptyHint.d.ts.map +1 -1
- package/dist/app/builder/EmptyHint.js +6 -1
- package/dist/app/builder/EmptyHint.js.map +1 -1
- package/dist/app/builder/LayoutSurface.d.ts +33 -9
- package/dist/app/builder/LayoutSurface.d.ts.map +1 -1
- package/dist/app/builder/LayoutSurface.js +74 -23
- package/dist/app/builder/LayoutSurface.js.map +1 -1
- package/dist/app/builder/PipelineStrip.d.ts +5 -2
- package/dist/app/builder/PipelineStrip.d.ts.map +1 -1
- package/dist/app/builder/PipelineStrip.js +33 -15
- package/dist/app/builder/PipelineStrip.js.map +1 -1
- package/dist/app/builder/SaveDialog.d.ts +9 -1
- package/dist/app/builder/SaveDialog.d.ts.map +1 -1
- package/dist/app/builder/SaveDialog.js +9 -3
- package/dist/app/builder/SaveDialog.js.map +1 -1
- package/dist/app/builder/Toolbar.d.ts +14 -4
- package/dist/app/builder/Toolbar.d.ts.map +1 -1
- package/dist/app/builder/Toolbar.js +24 -7
- package/dist/app/builder/Toolbar.js.map +1 -1
- package/dist/app/builder/Workspace.d.ts +23 -3
- package/dist/app/builder/Workspace.d.ts.map +1 -1
- package/dist/app/builder/Workspace.js +58 -8
- package/dist/app/builder/Workspace.js.map +1 -1
- package/dist/app/builder/builder-model.d.ts +146 -3
- package/dist/app/builder/builder-model.d.ts.map +1 -1
- package/dist/app/builder/builder-model.js +196 -5
- package/dist/app/builder/builder-model.js.map +1 -1
- package/dist/app/builder/labels.d.ts +13 -62
- package/dist/app/builder/labels.d.ts.map +1 -1
- package/dist/app/builder/labels.js +9 -58
- package/dist/app/builder/labels.js.map +1 -1
- package/dist/app/builder/reveal.d.ts +10 -0
- package/dist/app/builder/reveal.d.ts.map +1 -0
- package/dist/app/builder/reveal.js +10 -0
- package/dist/app/builder/reveal.js.map +1 -0
- package/dist/app/builder/status-chip.d.ts.map +1 -1
- package/dist/app/builder/status-chip.js +3 -2
- package/dist/app/builder/status-chip.js.map +1 -1
- package/dist/app/builder/use-builder-catalogue.d.ts +5 -1
- package/dist/app/builder/use-builder-catalogue.d.ts.map +1 -1
- package/dist/app/builder/use-builder-catalogue.js +50 -17
- package/dist/app/builder/use-builder-catalogue.js.map +1 -1
- package/dist/app/builder/use-builder-session.d.ts +30 -0
- package/dist/app/builder/use-builder-session.d.ts.map +1 -0
- package/dist/app/builder/use-builder-session.js +58 -0
- package/dist/app/builder/use-builder-session.js.map +1 -0
- package/dist/app/builder/use-display-resolver.d.ts +17 -0
- package/dist/app/builder/use-display-resolver.d.ts.map +1 -0
- package/dist/app/builder/use-display-resolver.js +16 -0
- package/dist/app/builder/use-display-resolver.js.map +1 -0
- package/dist/app/builder/use-save-dashboard.d.ts +3 -1
- package/dist/app/builder/use-save-dashboard.d.ts.map +1 -1
- package/dist/app/builder/use-save-dashboard.js +3 -1
- package/dist/app/builder/use-save-dashboard.js.map +1 -1
- package/dist/app/index.d.ts +8 -3
- package/dist/app/index.d.ts.map +1 -1
- package/dist/app/index.js +8 -2
- package/dist/app/index.js.map +1 -1
- package/dist/app/layout-builder.d.ts +18 -25
- package/dist/app/layout-builder.d.ts.map +1 -1
- package/dist/app/layout-builder.js +84 -78
- package/dist/app/layout-builder.js.map +1 -1
- package/dist/app/mcp-app-view-chrome.d.ts +103 -20
- package/dist/app/mcp-app-view-chrome.d.ts.map +1 -1
- package/dist/app/mcp-app-view-chrome.js +125 -40
- package/dist/app/mcp-app-view-chrome.js.map +1 -1
- package/dist/app/mcp-app-view-states.d.ts +23 -0
- package/dist/app/mcp-app-view-states.d.ts.map +1 -0
- package/dist/app/mcp-app-view-states.js +55 -0
- package/dist/app/mcp-app-view-states.js.map +1 -0
- package/dist/app/mcp-app-view.d.ts +72 -5
- package/dist/app/mcp-app-view.d.ts.map +1 -1
- package/dist/app/mcp-app-view.js +241 -141
- package/dist/app/mcp-app-view.js.map +1 -1
- package/dist/app/mcp-toolkit-app.d.ts +8 -2
- package/dist/app/mcp-toolkit-app.d.ts.map +1 -1
- package/dist/app/mcp-toolkit-app.js +33 -4
- package/dist/app/mcp-toolkit-app.js.map +1 -1
- package/dist/app/mcp-use-host-bridge.d.ts +15 -6
- package/dist/app/mcp-use-host-bridge.d.ts.map +1 -1
- package/dist/app/mcp-use-host-bridge.js +51 -22
- package/dist/app/mcp-use-host-bridge.js.map +1 -1
- package/dist/app/model-context.d.ts +71 -0
- package/dist/app/model-context.d.ts.map +1 -0
- package/dist/app/model-context.js +101 -0
- package/dist/app/model-context.js.map +1 -0
- package/dist/app/use-build-mode-focus.d.ts +33 -0
- package/dist/app/use-build-mode-focus.d.ts.map +1 -0
- package/dist/app/use-build-mode-focus.js +59 -0
- package/dist/app/use-build-mode-focus.js.map +1 -0
- package/dist/app/use-view-actions.d.ts +31 -0
- package/dist/app/use-view-actions.d.ts.map +1 -0
- package/dist/app/use-view-actions.js +81 -0
- package/dist/app/use-view-actions.js.map +1 -0
- package/dist/app/use-view-lifecycle.d.ts +42 -0
- package/dist/app/use-view-lifecycle.d.ts.map +1 -0
- package/dist/app/use-view-lifecycle.js +81 -0
- package/dist/app/use-view-lifecycle.js.map +1 -0
- package/dist/app/view-lifecycle.d.ts +185 -0
- package/dist/app/view-lifecycle.d.ts.map +1 -0
- package/dist/app/view-lifecycle.js +207 -0
- package/dist/app/view-lifecycle.js.map +1 -0
- package/dist/app/widget-fixture.d.ts +10 -3
- package/dist/app/widget-fixture.d.ts.map +1 -1
- package/dist/app/widget-fixture.js +21 -8
- package/dist/app/widget-fixture.js.map +1 -1
- package/dist/app/widget-props-sheet.d.ts +6 -10
- package/dist/app/widget-props-sheet.d.ts.map +1 -1
- package/dist/app/widget-props-sheet.js +25 -20
- package/dist/app/widget-props-sheet.js.map +1 -1
- package/dist/app/widget-renderer.d.ts +41 -1
- package/dist/app/widget-renderer.d.ts.map +1 -1
- package/dist/app/widget-renderer.js +82 -31
- package/dist/app/widget-renderer.js.map +1 -1
- package/dist/components/DrillButton.d.ts +9 -6
- package/dist/components/DrillButton.d.ts.map +1 -1
- package/dist/components/DrillButton.js +9 -6
- package/dist/components/DrillButton.js.map +1 -1
- package/dist/components/EmptyState.d.ts +33 -0
- package/dist/components/EmptyState.d.ts.map +1 -0
- package/dist/components/EmptyState.js +19 -0
- package/dist/components/EmptyState.js.map +1 -0
- package/dist/components/ErrorState.d.ts +53 -0
- package/dist/components/ErrorState.d.ts.map +1 -0
- package/dist/components/ErrorState.js +77 -0
- package/dist/components/ErrorState.js.map +1 -0
- package/dist/components/FilterBar.d.ts +16 -5
- package/dist/components/FilterBar.d.ts.map +1 -1
- package/dist/components/FilterBar.js +13 -5
- package/dist/components/FilterBar.js.map +1 -1
- package/dist/components/GroupCard.d.ts.map +1 -1
- package/dist/components/GroupCard.js +2 -1
- package/dist/components/GroupCard.js.map +1 -1
- package/dist/components/KpiGrid.d.ts +70 -18
- package/dist/components/KpiGrid.d.ts.map +1 -1
- package/dist/components/KpiGrid.js +112 -23
- package/dist/components/KpiGrid.js.map +1 -1
- package/dist/components/ListFooter.d.ts +32 -4
- package/dist/components/ListFooter.d.ts.map +1 -1
- package/dist/components/ListFooter.js +35 -6
- package/dist/components/ListFooter.js.map +1 -1
- package/dist/components/PagedListFooter.d.ts +57 -0
- package/dist/components/PagedListFooter.d.ts.map +1 -0
- package/dist/components/PagedListFooter.js +27 -0
- package/dist/components/PagedListFooter.js.map +1 -0
- package/dist/components/Pills.d.ts +36 -12
- package/dist/components/Pills.d.ts.map +1 -1
- package/dist/components/Pills.js +29 -8
- package/dist/components/Pills.js.map +1 -1
- package/dist/components/SectionHeading.d.ts +3 -1
- package/dist/components/SectionHeading.d.ts.map +1 -1
- package/dist/components/SectionHeading.js +6 -2
- package/dist/components/SectionHeading.js.map +1 -1
- package/dist/components/Toast.d.ts +43 -0
- package/dist/components/Toast.d.ts.map +1 -0
- package/dist/components/Toast.js +106 -0
- package/dist/components/Toast.js.map +1 -0
- package/dist/components/WidgetHeader.d.ts +34 -10
- package/dist/components/WidgetHeader.d.ts.map +1 -1
- package/dist/components/WidgetHeader.js +11 -6
- package/dist/components/WidgetHeader.js.map +1 -1
- package/dist/hooks/index.d.ts +4 -4
- package/dist/hooks/index.d.ts.map +1 -1
- package/dist/hooks/index.js +1 -1
- package/dist/hooks/index.js.map +1 -1
- package/dist/hooks/tool-result-recovery-model.d.ts +155 -0
- package/dist/hooks/tool-result-recovery-model.d.ts.map +1 -0
- package/dist/hooks/tool-result-recovery-model.js +273 -0
- package/dist/hooks/tool-result-recovery-model.js.map +1 -0
- package/dist/hooks/use-tool-query.d.ts +56 -14
- package/dist/hooks/use-tool-query.d.ts.map +1 -1
- package/dist/hooks/use-tool-query.js +102 -25
- package/dist/hooks/use-tool-query.js.map +1 -1
- package/dist/hooks/use-tool-result-recovery.d.ts +61 -44
- package/dist/hooks/use-tool-result-recovery.d.ts.map +1 -1
- package/dist/hooks/use-tool-result-recovery.js +62 -110
- package/dist/hooks/use-tool-result-recovery.js.map +1 -1
- package/dist/hooks/use-view-data.d.ts +55 -7
- package/dist/hooks/use-view-data.d.ts.map +1 -1
- package/dist/hooks/use-view-data.js +81 -11
- package/dist/hooks/use-view-data.js.map +1 -1
- package/dist/hooks/use-view-tool-query.d.ts +12 -7
- package/dist/hooks/use-view-tool-query.d.ts.map +1 -1
- package/dist/hooks/use-view-tool-query.js +15 -14
- package/dist/hooks/use-view-tool-query.js.map +1 -1
- package/dist/index.d.ts +27 -13
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +29 -7
- package/dist/index.js.map +1 -1
- package/dist/lib/focus-return.d.ts +61 -0
- package/dist/lib/focus-return.d.ts.map +1 -0
- package/dist/lib/focus-return.js +46 -0
- package/dist/lib/focus-return.js.map +1 -0
- package/dist/lib/focus-ring.d.ts +18 -0
- package/dist/lib/focus-ring.d.ts.map +1 -0
- package/dist/lib/focus-ring.js +18 -0
- package/dist/lib/focus-ring.js.map +1 -0
- package/dist/lib/icon-stroke.d.ts +12 -0
- package/dist/lib/icon-stroke.d.ts.map +1 -0
- package/dist/lib/icon-stroke.js +12 -0
- package/dist/lib/icon-stroke.js.map +1 -0
- package/dist/lib/parse-tool-result.d.ts +23 -1
- package/dist/lib/parse-tool-result.d.ts.map +1 -1
- package/dist/lib/parse-tool-result.js +38 -2
- package/dist/lib/parse-tool-result.js.map +1 -1
- package/dist/lib/toast-model.d.ts +86 -0
- package/dist/lib/toast-model.d.ts.map +1 -0
- package/dist/lib/toast-model.js +102 -0
- package/dist/lib/toast-model.js.map +1 -0
- package/dist/lib/tone-utils.d.ts +95 -9
- package/dist/lib/tone-utils.d.ts.map +1 -1
- package/dist/lib/tone-utils.js +100 -9
- package/dist/lib/tone-utils.js.map +1 -1
- package/dist/lib/tool-query.d.ts +107 -0
- package/dist/lib/tool-query.d.ts.map +1 -0
- package/dist/lib/tool-query.js +182 -0
- package/dist/lib/tool-query.js.map +1 -0
- package/dist/lib/tool-result-observer.d.ts +108 -0
- package/dist/lib/tool-result-observer.d.ts.map +1 -0
- package/dist/lib/tool-result-observer.js +158 -0
- package/dist/lib/tool-result-observer.js.map +1 -0
- package/dist/lib/typography.d.ts +37 -0
- package/dist/lib/typography.d.ts.map +1 -0
- package/dist/lib/typography.js +41 -0
- package/dist/lib/typography.js.map +1 -0
- package/dist/lib/utils.d.ts.map +1 -1
- package/dist/lib/utils.js +11 -1
- package/dist/lib/utils.js.map +1 -1
- package/dist/locale/index.d.ts +3 -1
- package/dist/locale/index.d.ts.map +1 -1
- package/dist/locale/index.js +2 -1
- package/dist/locale/index.js.map +1 -1
- package/dist/locale/locale-provider.d.ts +42 -1
- package/dist/locale/locale-provider.d.ts.map +1 -1
- package/dist/locale/locale-provider.js +44 -3
- package/dist/locale/locale-provider.js.map +1 -1
- package/dist/locale/message-types.d.ts +336 -0
- package/dist/locale/message-types.d.ts.map +1 -0
- package/dist/locale/message-types.js +7 -0
- package/dist/locale/message-types.js.map +1 -0
- package/dist/locale/messages-de.d.ts +9 -0
- package/dist/locale/messages-de.d.ts.map +1 -0
- package/dist/locale/messages-de.js +185 -0
- package/dist/locale/messages-de.js.map +1 -0
- package/dist/locale/messages-en.d.ts +8 -0
- package/dist/locale/messages-en.d.ts.map +1 -0
- package/dist/locale/messages-en.js +184 -0
- package/dist/locale/messages-en.js.map +1 -0
- package/dist/locale/toolkit-messages.d.ts +57 -0
- package/dist/locale/toolkit-messages.d.ts.map +1 -0
- package/dist/locale/toolkit-messages.js +103 -0
- package/dist/locale/toolkit-messages.js.map +1 -0
- package/dist/primitives/alert.d.ts +1 -1
- package/dist/primitives/alert.d.ts.map +1 -1
- package/dist/primitives/alert.js +6 -2
- package/dist/primitives/alert.js.map +1 -1
- package/dist/primitives/badge.d.ts +1 -1
- package/dist/primitives/badge.d.ts.map +1 -1
- package/dist/primitives/badge.js +19 -6
- package/dist/primitives/badge.js.map +1 -1
- package/dist/primitives/button.d.ts +1 -1
- package/dist/primitives/button.d.ts.map +1 -1
- package/dist/primitives/button.js +12 -8
- package/dist/primitives/button.js.map +1 -1
- package/dist/primitives/card.js +4 -4
- package/dist/primitives/card.js.map +1 -1
- package/dist/primitives/dialog.d.ts +7 -3
- package/dist/primitives/dialog.d.ts.map +1 -1
- package/dist/primitives/dialog.js +22 -8
- package/dist/primitives/dialog.js.map +1 -1
- package/dist/primitives/input.d.ts.map +1 -1
- package/dist/primitives/input.js +4 -1
- package/dist/primitives/input.js.map +1 -1
- package/dist/primitives/scroll-area.js +1 -1
- package/dist/primitives/scroll-area.js.map +1 -1
- package/dist/primitives/select.d.ts.map +1 -1
- package/dist/primitives/select.js +6 -3
- package/dist/primitives/select.js.map +1 -1
- package/dist/primitives/sheet.d.ts +3 -1
- package/dist/primitives/sheet.d.ts.map +1 -1
- package/dist/primitives/sheet.js +17 -7
- package/dist/primitives/sheet.js.map +1 -1
- package/dist/primitives/skeleton.js +1 -1
- package/dist/primitives/skeleton.js.map +1 -1
- package/dist/primitives/switch.d.ts.map +1 -1
- package/dist/primitives/switch.js +2 -1
- package/dist/primitives/switch.js.map +1 -1
- package/dist/primitives/tabs.d.ts.map +1 -1
- package/dist/primitives/tabs.js +5 -3
- package/dist/primitives/tabs.js.map +1 -1
- package/dist/providers/query-provider.d.ts +32 -1
- package/dist/providers/query-provider.d.ts.map +1 -1
- package/dist/providers/query-provider.js +53 -4
- package/dist/providers/query-provider.js.map +1 -1
- package/dist/render-cases-primitives.js +1 -1
- package/dist/render-cases-primitives.js.map +1 -1
- package/dist/render-cases.d.ts.map +1 -1
- package/dist/render-cases.js +48 -6
- package/dist/render-cases.js.map +1 -1
- package/dist/render-effects.d.ts +42 -0
- package/dist/render-effects.d.ts.map +1 -0
- package/dist/render-effects.js +81 -0
- package/dist/render-effects.js.map +1 -0
- package/dist/render-scan.d.ts +25 -0
- package/dist/render-scan.d.ts.map +1 -0
- package/dist/render-scan.js +66 -0
- package/dist/render-scan.js.map +1 -0
- package/dist/theme/cd-tokens.d.ts +66 -0
- package/dist/theme/cd-tokens.d.ts.map +1 -0
- package/dist/theme/cd-tokens.js +64 -0
- package/dist/theme/cd-tokens.js.map +1 -0
- package/dist/theme/create-theme.d.ts +214 -39
- package/dist/theme/create-theme.d.ts.map +1 -1
- package/dist/theme/create-theme.js +204 -13
- package/dist/theme/create-theme.js.map +1 -1
- package/dist/theme/fonts.d.ts +38 -0
- package/dist/theme/fonts.d.ts.map +1 -0
- package/dist/theme/fonts.js +56 -0
- package/dist/theme/fonts.js.map +1 -0
- package/dist/theme/host-fonts.d.ts +39 -0
- package/dist/theme/host-fonts.d.ts.map +1 -0
- package/dist/theme/host-fonts.js +44 -0
- package/dist/theme/host-fonts.js.map +1 -0
- package/dist/theme/index.d.ts +8 -1
- package/dist/theme/index.d.ts.map +1 -1
- package/dist/theme/index.js +5 -1
- package/dist/theme/index.js.map +1 -1
- package/dist/theme/portal-container.d.ts +16 -0
- package/dist/theme/portal-container.d.ts.map +1 -0
- package/dist/theme/portal-container.js +19 -0
- package/dist/theme/portal-container.js.map +1 -0
- package/dist/theme/presets.d.ts +24 -9
- package/dist/theme/presets.d.ts.map +1 -1
- package/dist/theme/presets.js +44 -11
- package/dist/theme/presets.js.map +1 -1
- package/dist/theme/theme-provider.d.ts +27 -9
- package/dist/theme/theme-provider.d.ts.map +1 -1
- package/dist/theme/theme-provider.js +42 -20
- package/dist/theme/theme-provider.js.map +1 -1
- package/package.json +11 -5
- package/src/app/adapt-data-widget.tsx +2 -42
- package/src/app/builder/BuilderBanners.tsx +26 -13
- package/src/app/builder/CanvasRow.tsx +79 -32
- package/src/app/builder/CatalogueSheet.tsx +58 -35
- package/src/app/builder/CellPropsSheet.tsx +17 -2
- package/src/app/builder/DiscardDialog.tsx +59 -0
- package/src/app/builder/EmptyHint.tsx +16 -11
- package/src/app/builder/LayoutSurface.tsx +207 -67
- package/src/app/builder/PipelineStrip.tsx +265 -156
- package/src/app/builder/SaveDialog.tsx +25 -14
- package/src/app/builder/Toolbar.tsx +154 -57
- package/src/app/builder/Workspace.tsx +226 -56
- package/src/app/builder/builder-feedback.test.tsx +75 -0
- package/src/app/builder/builder-model.test.ts +5 -0
- package/src/app/builder/builder-model.ts +346 -6
- package/src/app/builder/builder-model.ux.test.ts +456 -0
- package/src/app/builder/builder-ux.test.tsx +844 -0
- package/src/app/builder/labels.ts +15 -121
- package/src/app/builder/reveal.ts +10 -0
- package/src/app/builder/status-chip.tsx +8 -4
- package/src/app/builder/use-builder-catalogue.ts +62 -19
- package/src/app/builder/use-builder-session.ts +68 -0
- package/src/app/builder/use-display-resolver.ts +24 -0
- package/src/app/builder/use-save-dashboard.ts +5 -0
- package/src/app/index.ts +20 -3
- package/src/app/layout-builder.tsx +193 -186
- package/src/app/mcp-app-view-chrome.test.tsx +487 -14
- package/src/app/mcp-app-view-chrome.tsx +328 -100
- package/src/app/mcp-app-view-states.tsx +140 -0
- package/src/app/mcp-app-view.effects.test.tsx +292 -0
- package/src/app/mcp-app-view.test.tsx +478 -0
- package/src/app/mcp-app-view.tsx +447 -190
- package/src/app/mcp-toolkit-app.test.tsx +40 -0
- package/src/app/mcp-toolkit-app.tsx +39 -8
- package/src/app/mcp-use-host-bridge.test.tsx +180 -0
- package/src/app/mcp-use-host-bridge.tsx +67 -24
- package/src/app/model-context.test.tsx +116 -0
- package/src/app/model-context.tsx +125 -0
- package/src/app/use-build-mode-focus.ts +62 -0
- package/src/app/use-view-actions.ts +89 -0
- package/src/app/use-view-lifecycle.ts +122 -0
- package/src/app/view-lifecycle.test.ts +443 -0
- package/src/app/view-lifecycle.ts +334 -0
- package/src/app/widget-fixture.effects.test.tsx +51 -0
- package/src/app/widget-fixture.render.test.tsx +81 -0
- package/src/app/widget-fixture.tsx +34 -11
- package/src/app/widget-props-sheet.tsx +67 -39
- package/src/app/widget-renderer.render.test.tsx +131 -0
- package/src/app/widget-renderer.tsx +136 -38
- package/src/components/DrillButton.tsx +24 -10
- package/src/components/EmptyState.tsx +83 -0
- package/src/components/ErrorState.tsx +204 -0
- package/src/components/FilterBar.test.tsx +82 -0
- package/src/components/FilterBar.tsx +56 -27
- package/src/components/GroupCard.tsx +3 -2
- package/src/components/KpiGrid.test.tsx +279 -0
- package/src/components/KpiGrid.tsx +329 -91
- package/src/components/ListFooter.test.tsx +116 -0
- package/src/components/ListFooter.tsx +110 -12
- package/src/components/PagedListFooter.test.tsx +140 -0
- package/src/components/PagedListFooter.tsx +107 -0
- package/src/components/Pills.test.tsx +77 -0
- package/src/components/Pills.tsx +78 -16
- package/src/components/SectionHeading.tsx +9 -3
- package/src/components/Toast.tsx +206 -0
- package/src/components/WidgetHeader.test.tsx +78 -0
- package/src/components/WidgetHeader.tsx +63 -16
- package/src/components/feedback-states.test.tsx +314 -0
- package/src/components/tone-figures.test.tsx +58 -0
- package/src/fonts.css +19 -0
- package/src/globals.css +9 -165
- package/src/hooks/index.ts +6 -3
- package/src/hooks/tool-result-recovery-model.test.ts +744 -0
- package/src/hooks/tool-result-recovery-model.ts +418 -0
- package/src/hooks/use-tool-query.effects.test.tsx +205 -0
- package/src/hooks/use-tool-query.ts +156 -33
- package/src/hooks/use-tool-result-recovery.effects.test.tsx +141 -0
- package/src/hooks/use-tool-result-recovery.test.ts +28 -5
- package/src/hooks/use-tool-result-recovery.ts +101 -131
- package/src/hooks/use-view-data.test.tsx +169 -0
- package/src/hooks/use-view-data.ts +131 -10
- package/src/hooks/use-view-tool-query.ts +25 -19
- package/src/i18n-coverage.test.tsx +425 -0
- package/src/index.ts +102 -13
- package/src/lib/focus-return.test.ts +288 -0
- package/src/lib/focus-return.ts +96 -0
- package/src/lib/focus-ring.ts +20 -0
- package/src/lib/icon-stroke.test.ts +59 -0
- package/src/lib/icon-stroke.ts +13 -0
- package/src/lib/parse-tool-result.test.ts +46 -1
- package/src/lib/parse-tool-result.ts +40 -2
- package/src/lib/toast-model.test.ts +233 -0
- package/src/lib/toast-model.ts +165 -0
- package/src/lib/tone-utils.test.ts +125 -16
- package/src/lib/tone-utils.ts +144 -15
- package/src/lib/tool-query.test.ts +569 -0
- package/src/lib/tool-query.ts +253 -0
- package/src/lib/tool-result-observer.test.ts +296 -0
- package/src/lib/tool-result-observer.ts +211 -0
- package/src/lib/typography.test.ts +45 -0
- package/src/lib/typography.ts +47 -0
- package/src/lib/utils.ts +12 -1
- package/src/locale/index.ts +14 -1
- package/src/locale/locale-provider.test.tsx +87 -0
- package/src/locale/locale-provider.tsx +90 -3
- package/src/locale/message-types.ts +337 -0
- package/src/locale/messages-de.ts +198 -0
- package/src/locale/messages-en.ts +196 -0
- package/src/locale/toolkit-messages.test.ts +349 -0
- package/src/locale/toolkit-messages.ts +143 -0
- package/src/no-hardcoded-copy.test.ts +432 -0
- package/src/primitives/alert.tsx +7 -2
- package/src/primitives/badge.tsx +19 -7
- package/src/primitives/button.tsx +13 -8
- package/src/primitives/card.tsx +4 -4
- package/src/primitives/dialog.tsx +42 -8
- package/src/primitives/input.tsx +5 -3
- package/src/primitives/scroll-area.tsx +1 -1
- package/src/primitives/select.tsx +7 -4
- package/src/primitives/sheet.tsx +33 -6
- package/src/primitives/skeleton.tsx +1 -1
- package/src/primitives/switch.tsx +4 -2
- package/src/primitives/tabs.tsx +9 -6
- package/src/providers/query-provider.test.tsx +154 -0
- package/src/providers/query-provider.tsx +66 -5
- package/src/render-cases-primitives.tsx +1 -1
- package/src/render-cases.tsx +82 -6
- package/src/render-effects.tsx +96 -0
- package/src/render-scan.ts +75 -0
- package/src/theme/cd-tokens.generated.css +48 -0
- package/src/theme/cd-tokens.test.ts +109 -0
- package/src/theme/cd-tokens.ts +67 -0
- package/src/theme/create-theme.test.ts +253 -5
- package/src/theme/create-theme.ts +341 -41
- package/src/theme/fonts.test.ts +85 -0
- package/src/theme/fonts.ts +72 -0
- package/src/theme/host-fonts.test.ts +135 -0
- package/src/theme/host-fonts.ts +52 -0
- package/src/theme/index.ts +15 -1
- package/src/theme/portal-container.ts +20 -0
- package/src/theme/presets.ts +44 -11
- package/src/theme/theme-css.test.ts +619 -0
- package/src/theme/theme-provider.test.tsx +82 -0
- package/src/theme/theme-provider.tsx +60 -24
- package/src/theme.css +344 -0
- package/ui-catalog.json +783 -49
package/src/render-cases.tsx
CHANGED
|
@@ -1,24 +1,31 @@
|
|
|
1
1
|
import type { ReactElement } from "react"
|
|
2
|
+
import { ExternalLink, Inbox } from "lucide-react"
|
|
2
3
|
import {
|
|
3
4
|
Button,
|
|
4
5
|
CountPill,
|
|
5
6
|
DrillButton,
|
|
7
|
+
EmptyState,
|
|
8
|
+
ErrorState,
|
|
6
9
|
FilterBar,
|
|
7
10
|
GridItem,
|
|
8
11
|
GridLayout,
|
|
9
12
|
GroupCard,
|
|
10
13
|
KpiGrid,
|
|
14
|
+
KpiGridSkeleton,
|
|
11
15
|
ListFooter,
|
|
12
16
|
LivePill,
|
|
13
17
|
LocaleProvider,
|
|
18
|
+
PagedListFooter,
|
|
14
19
|
SectionHeading,
|
|
20
|
+
StatusBadge,
|
|
15
21
|
ThemeProvider,
|
|
16
22
|
themePresets,
|
|
23
|
+
ToastProvider,
|
|
17
24
|
useLocale,
|
|
18
25
|
WidgetHeader,
|
|
19
26
|
} from "./index.js"
|
|
20
27
|
import { createStandaloneHostBridge, HostBridgeProvider, useHostBridge } from "./app/host-bridge.js"
|
|
21
|
-
import { HostModelContext } from "./app/
|
|
28
|
+
import { HostModelContext } from "./app/model-context.js"
|
|
22
29
|
import { WidgetFixtureHost, type FixtureWidget } from "./app/widget-fixture.js"
|
|
23
30
|
import { PRIMITIVE_RENDER_CASES, type RenderCase } from "./render-cases-primitives.js"
|
|
24
31
|
|
|
@@ -107,11 +114,17 @@ export const RENDER_CASES: RenderCase[] = [
|
|
|
107
114
|
trendDirection: "up",
|
|
108
115
|
},
|
|
109
116
|
{ label: "Done", value: 12, fraction: "/19", tone: "success" },
|
|
110
|
-
{ label: "Total", value: 19, onClick: noop,
|
|
117
|
+
{ label: "Total", value: 19, onClick: noop, actionHint: "Shows all orders" },
|
|
111
118
|
]}
|
|
112
119
|
/>
|
|
113
120
|
),
|
|
114
121
|
},
|
|
122
|
+
{
|
|
123
|
+
// A skeleton has no text; the marker is its busy state.
|
|
124
|
+
name: "KpiGridSkeleton",
|
|
125
|
+
marker: 'aria-busy="true"',
|
|
126
|
+
render: () => <KpiGridSkeleton cells={4} boxed />,
|
|
127
|
+
},
|
|
115
128
|
{
|
|
116
129
|
name: "LivePill",
|
|
117
130
|
marker: "RC:LivePill",
|
|
@@ -122,6 +135,11 @@ export const RENDER_CASES: RenderCase[] = [
|
|
|
122
135
|
marker: "RC:CountPill",
|
|
123
136
|
render: () => <CountPill tone="warning">RC:CountPill</CountPill>,
|
|
124
137
|
},
|
|
138
|
+
{
|
|
139
|
+
name: "StatusBadge",
|
|
140
|
+
marker: "RC:StatusBadge",
|
|
141
|
+
render: () => <StatusBadge tone="warning">RC:StatusBadge</StatusBadge>,
|
|
142
|
+
},
|
|
125
143
|
{
|
|
126
144
|
name: "SectionHeading",
|
|
127
145
|
marker: "RC:SectionHeading",
|
|
@@ -132,9 +150,9 @@ export const RENDER_CASES: RenderCase[] = [
|
|
|
132
150
|
marker: "RC:WidgetHeader",
|
|
133
151
|
render: () => (
|
|
134
152
|
<WidgetHeader
|
|
135
|
-
|
|
136
|
-
iconTone="info"
|
|
153
|
+
as="h2"
|
|
137
154
|
title="RC:WidgetHeader"
|
|
155
|
+
badge={<StatusBadge tone="info">Running</StatusBadge>}
|
|
138
156
|
sub={<LivePill>Live</LivePill>}
|
|
139
157
|
actions={
|
|
140
158
|
<Button size="sm" variant="ghost" onClick={noop}>
|
|
@@ -174,7 +192,7 @@ export const RENDER_CASES: RenderCase[] = [
|
|
|
174
192
|
name: "DrillButton",
|
|
175
193
|
marker: "RC:DrillButton",
|
|
176
194
|
render: () => (
|
|
177
|
-
<DrillButton onDrill={noop} icon=
|
|
195
|
+
<DrillButton onDrill={noop} icon={<ExternalLink />} size="sm" ariaLabel="Open order o-1001">
|
|
178
196
|
RC:DrillButton
|
|
179
197
|
</DrillButton>
|
|
180
198
|
),
|
|
@@ -184,6 +202,64 @@ export const RENDER_CASES: RenderCase[] = [
|
|
|
184
202
|
marker: "of 42 tasks",
|
|
185
203
|
render: () => <ListFooter shown={8} total={42} hasMore onLoadMore={noop} noun="tasks" />,
|
|
186
204
|
},
|
|
205
|
+
{
|
|
206
|
+
name: "PagedListFooter",
|
|
207
|
+
marker: "of 3 orders",
|
|
208
|
+
render: () => (
|
|
209
|
+
<PagedListFooter
|
|
210
|
+
paged={{
|
|
211
|
+
items: ["o-1", "o-2"],
|
|
212
|
+
total: 3,
|
|
213
|
+
hasMore: true,
|
|
214
|
+
loadMore: noop,
|
|
215
|
+
refreshing: true,
|
|
216
|
+
firstPage: {},
|
|
217
|
+
loadMoreError: new Error("HTTP 503"),
|
|
218
|
+
}}
|
|
219
|
+
noun="orders"
|
|
220
|
+
/>
|
|
221
|
+
),
|
|
222
|
+
},
|
|
223
|
+
|
|
224
|
+
// ── Feedback and states ──
|
|
225
|
+
{
|
|
226
|
+
// The provider renders its children plus the (empty) live region.
|
|
227
|
+
name: "ToastProvider",
|
|
228
|
+
marker: "RC:ToastProvider",
|
|
229
|
+
render: () => (
|
|
230
|
+
<ToastProvider>
|
|
231
|
+
<div>RC:ToastProvider</div>
|
|
232
|
+
</ToastProvider>
|
|
233
|
+
),
|
|
234
|
+
},
|
|
235
|
+
{
|
|
236
|
+
name: "EmptyState",
|
|
237
|
+
marker: "RC:EmptyState",
|
|
238
|
+
render: () => (
|
|
239
|
+
<EmptyState
|
|
240
|
+
icon={<Inbox />}
|
|
241
|
+
title="RC:EmptyState"
|
|
242
|
+
description="No orders in this period."
|
|
243
|
+
action={
|
|
244
|
+
<Button size="sm" onClick={noop}>
|
|
245
|
+
New order
|
|
246
|
+
</Button>
|
|
247
|
+
}
|
|
248
|
+
/>
|
|
249
|
+
),
|
|
250
|
+
},
|
|
251
|
+
{
|
|
252
|
+
name: "ErrorState",
|
|
253
|
+
marker: "RC:ErrorState",
|
|
254
|
+
render: () => (
|
|
255
|
+
<ErrorState
|
|
256
|
+
title="RC:ErrorState"
|
|
257
|
+
description="Check the connection and try again."
|
|
258
|
+
details="HTTP 503 Service Unavailable"
|
|
259
|
+
onRetry={noop}
|
|
260
|
+
/>
|
|
261
|
+
),
|
|
262
|
+
},
|
|
187
263
|
|
|
188
264
|
// ── Host seam / providers ──
|
|
189
265
|
{
|
|
@@ -212,7 +288,7 @@ export const RENDER_CASES: RenderCase[] = [
|
|
|
212
288
|
name: "ThemeProvider",
|
|
213
289
|
marker: "RC:ThemeProvider",
|
|
214
290
|
render: () => (
|
|
215
|
-
<ThemeProvider theme={themePresets.
|
|
291
|
+
<ThemeProvider theme={themePresets.emerald} mode="dark">
|
|
216
292
|
<div>RC:ThemeProvider</div>
|
|
217
293
|
</ThemeProvider>
|
|
218
294
|
),
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Effect-running renders for the WIRING tests SSR cannot see: effects,
|
|
3
|
+
* subscriptions and timers of the view lifecycle and the data hooks
|
|
4
|
+
* (toolkit#176 review). `react-dom/client` + `act` in a test file that opts
|
|
5
|
+
* into a DOM with `// @vitest-environment happy-dom`. Not an interaction kit:
|
|
6
|
+
* the house render path stays SSR (`renderToStaticMarkup`), and these tests
|
|
7
|
+
* drive hooks through their inputs; a `click()` only where the wiring starts
|
|
8
|
+
* at a button.
|
|
9
|
+
*/
|
|
10
|
+
import { act, useEffect, type ReactNode } from "react"
|
|
11
|
+
import { createRoot } from "react-dom/client"
|
|
12
|
+
|
|
13
|
+
// React warns about updates outside act() unless the runtime says it is a test.
|
|
14
|
+
;(globalThis as { IS_REACT_ACT_ENVIRONMENT?: boolean }).IS_REACT_ACT_ENVIRONMENT = true
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* Run `work` in an ASYNC act scope: the promises it starts (a tool call that
|
|
18
|
+
* resolves, a state update after it) settle, and their renders commit,
|
|
19
|
+
* before the scope ends.
|
|
20
|
+
*/
|
|
21
|
+
export function inAct(work: () => unknown): Promise<void> {
|
|
22
|
+
return act(() => {
|
|
23
|
+
work()
|
|
24
|
+
return Promise.resolve()
|
|
25
|
+
})
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
export interface EffectRender {
|
|
29
|
+
container: HTMLElement
|
|
30
|
+
/** Render `node` into the same root (a new host state, new props). */
|
|
31
|
+
rerender: (node: ReactNode) => Promise<void>
|
|
32
|
+
/** Unmount and run the cleanups; a second call does nothing. */
|
|
33
|
+
unmount: () => Promise<void>
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
/** Mount `node` and run its effects. */
|
|
37
|
+
export async function renderWithEffects(node: ReactNode): Promise<EffectRender> {
|
|
38
|
+
const container = document.createElement("div")
|
|
39
|
+
document.body.append(container)
|
|
40
|
+
const root = createRoot(container)
|
|
41
|
+
await inAct(() => root.render(node))
|
|
42
|
+
let mounted = true
|
|
43
|
+
return {
|
|
44
|
+
container,
|
|
45
|
+
rerender: (next) => inAct(() => root.render(next)),
|
|
46
|
+
unmount: async () => {
|
|
47
|
+
if (!mounted) return
|
|
48
|
+
mounted = false
|
|
49
|
+
await inAct(() => root.unmount())
|
|
50
|
+
container.remove()
|
|
51
|
+
},
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
/**
|
|
56
|
+
* Settle pending promises and the effects and renders they cause, with real
|
|
57
|
+
* timers: TanStack Query notifies its observers on a 0 ms timer, so each
|
|
58
|
+
* round lets one land (under fake timers use {@link advanceTimers}).
|
|
59
|
+
*/
|
|
60
|
+
export async function flushEffects(rounds = 3): Promise<void> {
|
|
61
|
+
for (let round = 0; round < rounds; round++) {
|
|
62
|
+
await act(async () => {
|
|
63
|
+
await new Promise((resolve) => setTimeout(resolve, 0))
|
|
64
|
+
})
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
/** Advance fake timers by `ms` inside act, so the renders they cause commit. */
|
|
69
|
+
export function advanceTimers(advance: (ms: number) => unknown, ms: number): Promise<void> {
|
|
70
|
+
return inAct(() => advance(ms))
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
/**
|
|
74
|
+
* Renders `useValue` in a probe and keeps its latest committed value: read
|
|
75
|
+
* `current` after a render or flush.
|
|
76
|
+
*/
|
|
77
|
+
export function hookProbe<T>(useValue: () => T): {
|
|
78
|
+
Probe: () => null
|
|
79
|
+
current: () => T
|
|
80
|
+
} {
|
|
81
|
+
const box: { value?: { current: T } } = {}
|
|
82
|
+
function Probe(): null {
|
|
83
|
+
const value = useValue()
|
|
84
|
+
useEffect(() => {
|
|
85
|
+
box.value = { current: value }
|
|
86
|
+
})
|
|
87
|
+
return null
|
|
88
|
+
}
|
|
89
|
+
return {
|
|
90
|
+
Probe,
|
|
91
|
+
current: () => {
|
|
92
|
+
if (!box.value) throw new Error("the probe has not committed yet")
|
|
93
|
+
return box.value.current
|
|
94
|
+
},
|
|
95
|
+
}
|
|
96
|
+
}
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Read SSR markup (`renderToStaticMarkup`) the way a user — sighted or with a
|
|
3
|
+
* screen reader — meets it: its text nodes plus the attributes that carry
|
|
4
|
+
* text (accessible names, tooltips, placeholders). DATA/TEST support module
|
|
5
|
+
* like `render-cases.tsx`: the a11y and i18n render suites scan through it,
|
|
6
|
+
* so it stays pure and dependency-free. React's SSR output is well-formed
|
|
7
|
+
* (attributes always double-quoted), which is what keeps these regexes honest.
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
/** Attributes whose value a user reads or hears. */
|
|
11
|
+
export const TEXT_ATTRIBUTES = [
|
|
12
|
+
"aria-label",
|
|
13
|
+
"aria-description",
|
|
14
|
+
"aria-roledescription",
|
|
15
|
+
"aria-valuetext",
|
|
16
|
+
"title",
|
|
17
|
+
"placeholder",
|
|
18
|
+
"alt",
|
|
19
|
+
] as const
|
|
20
|
+
|
|
21
|
+
const NAMED_ENTITIES: Record<string, string> = {
|
|
22
|
+
amp: "&",
|
|
23
|
+
lt: "<",
|
|
24
|
+
gt: ">",
|
|
25
|
+
quot: '"',
|
|
26
|
+
apos: "'",
|
|
27
|
+
nbsp: " ",
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
/** Decode the HTML entities React's SSR emits (named, decimal and hex). */
|
|
31
|
+
export function decodeEntities(text: string): string {
|
|
32
|
+
return text.replace(/&(#x[0-9a-f]+|#\d+|[a-z]+);/gi, (whole, ref: string) => {
|
|
33
|
+
if (ref.startsWith("#x") || ref.startsWith("#X")) {
|
|
34
|
+
return String.fromCodePoint(Number.parseInt(ref.slice(2), 16))
|
|
35
|
+
}
|
|
36
|
+
if (ref.startsWith("#")) return String.fromCodePoint(Number.parseInt(ref.slice(1), 10))
|
|
37
|
+
return NAMED_ENTITIES[ref.toLowerCase()] ?? whole
|
|
38
|
+
})
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
/** One piece of user-facing text in the markup. */
|
|
42
|
+
export interface MarkupText {
|
|
43
|
+
/** `"text"` for a text node, else the attribute name. */
|
|
44
|
+
source: string
|
|
45
|
+
value: string
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
/** Every non-blank text node and text-bearing attribute value, decoded. */
|
|
49
|
+
export function userFacingTexts(html: string): MarkupText[] {
|
|
50
|
+
const out: MarkupText[] = []
|
|
51
|
+
const withoutRawText = html.replace(/<(script|style)\b[^>]*>[\s\S]*?<\/\1>/gi, "")
|
|
52
|
+
for (const chunk of withoutRawText.split(/<[^>]*>/)) {
|
|
53
|
+
const value = decodeEntities(chunk).trim()
|
|
54
|
+
if (value) out.push({ source: "text", value })
|
|
55
|
+
}
|
|
56
|
+
for (const tag of withoutRawText.match(/<[a-z][^>]*>/gi) ?? []) {
|
|
57
|
+
for (const name of TEXT_ATTRIBUTES) {
|
|
58
|
+
const value = attribute(tag, name)
|
|
59
|
+
if (value?.trim()) out.push({ source: name, value: value.trim() })
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
return out
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
/** The opening tags of every element named `tag` (e.g. `"button"`). */
|
|
66
|
+
export function openingTags(html: string, tag: string): string[] {
|
|
67
|
+
return html.match(new RegExp(`<${tag}(?=[\\s>/])[^>]*>`, "gi")) ?? []
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
/** The decoded value of `name` on one opening tag, `undefined` when absent. */
|
|
71
|
+
export function attribute(openingTag: string, name: string): string | undefined {
|
|
72
|
+
const escaped = name.replace(/[-]/g, "\\-")
|
|
73
|
+
const match = new RegExp(`\\s${escaped}="([^"]*)"`, "i").exec(openingTag)
|
|
74
|
+
return match ? decodeEntities(match[1] ?? "") : undefined
|
|
75
|
+
}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
/* Aus Miragon/corporate-identity übernommen (miragon-brand 1.8.0, modeler-tool-design/assets/cd-tokens.generated.css). Nicht ändern, zum Aktualisieren neu aus der Skill kopieren. */
|
|
2
|
+
/* AUTOMATISCH GENERIERT aus brand/tokens.json. Nicht von Hand ändern, sondern die Quelle bearbeiten und `npm run tokens:build` laufen lassen. */
|
|
3
|
+
:root {
|
|
4
|
+
--cd-blau: #335DE5;
|
|
5
|
+
--cd-gruen: #00E676;
|
|
6
|
+
--cd-grau: #F9F7F7;
|
|
7
|
+
--cd-schwarz: #1D1D1D;
|
|
8
|
+
--cd-weiss: #FFFFFF;
|
|
9
|
+
--cd-blau-link: #2B50D4;
|
|
10
|
+
--cd-blau-hell: #6B8AFF;
|
|
11
|
+
--cd-success: #00E676;
|
|
12
|
+
--cd-success-soft: #DAFBEB;
|
|
13
|
+
--cd-success-hell: #00E676;
|
|
14
|
+
--cd-warning: #FFB000;
|
|
15
|
+
--cd-warning-soft: #FFF1D2;
|
|
16
|
+
--cd-warning-hell: #FFB000;
|
|
17
|
+
--cd-danger: #CD1839;
|
|
18
|
+
--cd-danger-soft: #FBEEF0;
|
|
19
|
+
--cd-danger-hell: #FB6D73;
|
|
20
|
+
--cd-info: #335DE5;
|
|
21
|
+
--cd-info-soft: #EEF1FD;
|
|
22
|
+
--cd-info-hell: #6B8AFF;
|
|
23
|
+
--cd-linie: #E6E2E2;
|
|
24
|
+
--cd-kontur: #8F8A8A;
|
|
25
|
+
--cd-text-leise: #6B6666;
|
|
26
|
+
--cd-gradient-brand: linear-gradient(120deg, #335DE5 30%, #00E676);
|
|
27
|
+
--cd-gradient-format: linear-gradient(135deg, #335DE5 0%, #00E676 140%);
|
|
28
|
+
--cd-space-1: 4px;
|
|
29
|
+
--cd-space-2: 8px;
|
|
30
|
+
--cd-space-3: 16px;
|
|
31
|
+
--cd-space-4: 24px;
|
|
32
|
+
--cd-space-5: 32px;
|
|
33
|
+
--cd-space-6: 48px;
|
|
34
|
+
--cd-space-7: 64px;
|
|
35
|
+
--cd-space-8: 96px;
|
|
36
|
+
--cd-radius-sm: 6px;
|
|
37
|
+
--cd-radius-md: 12px;
|
|
38
|
+
--cd-radius-lg: 16px;
|
|
39
|
+
--cd-radius-pill: 999px;
|
|
40
|
+
--cd-shadow-1: 0 1px 2px rgba(29, 29, 29, 0.06), 0 1px 3px rgba(29, 29, 29, 0.10);
|
|
41
|
+
--cd-shadow-2: 0 4px 12px rgba(29, 29, 29, 0.10);
|
|
42
|
+
--cd-shadow-3: 0 12px 32px rgba(29, 29, 29, 0.16);
|
|
43
|
+
--cd-motion-fast: 150ms;
|
|
44
|
+
--cd-motion-base: 250ms;
|
|
45
|
+
--cd-motion-slow: 400ms;
|
|
46
|
+
--cd-ease: cubic-bezier(0.4, 0, 0.2, 1);
|
|
47
|
+
--cd-ease-out: cubic-bezier(0, 0, 0.2, 1);
|
|
48
|
+
}
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
/// <reference types="node" />
|
|
2
|
+
import { createHash } from "node:crypto"
|
|
3
|
+
import { existsSync, readdirSync, readFileSync } from "node:fs"
|
|
4
|
+
import { homedir } from "node:os"
|
|
5
|
+
import { join } from "node:path"
|
|
6
|
+
import { describe, expect, it } from "vitest"
|
|
7
|
+
import { CD_TOKENS, CD_TOKENS_VERSION } from "./cd-tokens.js"
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* Drift guard for the vendored Miragon corporate-design tokens
|
|
11
|
+
* (modeler-tool-design §13): the copy must stay the skill's file, unchanged.
|
|
12
|
+
*
|
|
13
|
+
* `cd-tokens.generated.css` = ONE marker line + the upstream file byte for
|
|
14
|
+
* byte. Upstream is miragon-brand's `modeler-tool-design/assets/
|
|
15
|
+
* cd-tokens.generated.css`. When a checkout of the plugin is reachable
|
|
16
|
+
* (`MIRAGON_CD_TOKENS` or a Claude plugin cache under $HOME), the copy is
|
|
17
|
+
* compared to it directly; everywhere else (CI) the pinned hash below holds it.
|
|
18
|
+
*
|
|
19
|
+
* To re-vendor: copy the new upstream file below the marker line, update the
|
|
20
|
+
* version in the marker, CD_TOKENS_VERSION, UPSTREAM_SHA256 and CD_TOKENS,
|
|
21
|
+
* then copy the result to docs/.vitepress/theme/ (the docs site vendors the
|
|
22
|
+
* same file; examples/test/docs-theme.test.ts holds the two byte-identical).
|
|
23
|
+
*/
|
|
24
|
+
const UPSTREAM_SHA256 = "36d76f3a330a1250d332c6862be1dc4f7564d2461e7051d9a565ba723ef2c379"
|
|
25
|
+
const UPSTREAM_REL = join("skills", "modeler-tool-design", "assets", "cd-tokens.generated.css")
|
|
26
|
+
const MARKER =
|
|
27
|
+
`/* Aus Miragon/corporate-identity übernommen (miragon-brand ${CD_TOKENS_VERSION}, ` +
|
|
28
|
+
"modeler-tool-design/assets/cd-tokens.generated.css). Nicht ändern, zum Aktualisieren neu aus der Skill kopieren. */\n"
|
|
29
|
+
|
|
30
|
+
const vendored = readFileSync(new URL("./cd-tokens.generated.css", import.meta.url), "utf8")
|
|
31
|
+
const upstreamPart = vendored.slice(MARKER.length)
|
|
32
|
+
|
|
33
|
+
/** A reachable upstream copy of this version, or null (CI). */
|
|
34
|
+
function findUpstream(): string | null {
|
|
35
|
+
const explicit = process.env.MIRAGON_CD_TOKENS
|
|
36
|
+
if (explicit) return existsSync(explicit) ? explicit : null
|
|
37
|
+
const home = homedir()
|
|
38
|
+
let entries: string[]
|
|
39
|
+
try {
|
|
40
|
+
entries = readdirSync(home).filter((name) => name.startsWith(".claude"))
|
|
41
|
+
} catch {
|
|
42
|
+
return null
|
|
43
|
+
}
|
|
44
|
+
for (const dir of entries) {
|
|
45
|
+
const candidate = join(
|
|
46
|
+
home,
|
|
47
|
+
dir,
|
|
48
|
+
"plugins",
|
|
49
|
+
"cache",
|
|
50
|
+
"miragon-agent-skills",
|
|
51
|
+
"miragon-brand",
|
|
52
|
+
CD_TOKENS_VERSION,
|
|
53
|
+
UPSTREAM_REL,
|
|
54
|
+
)
|
|
55
|
+
if (existsSync(candidate)) return candidate
|
|
56
|
+
}
|
|
57
|
+
return null
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
/** `--cd-name: value;` declarations of the vendored `:root`. */
|
|
61
|
+
function cssTokens(css: string): Record<string, string> {
|
|
62
|
+
const out: Record<string, string> = {}
|
|
63
|
+
for (const match of css.matchAll(/--cd-([a-z0-9-]+):\s*([^;]+);/g)) {
|
|
64
|
+
out[match[1] as string] = (match[2] as string).trim()
|
|
65
|
+
}
|
|
66
|
+
return out
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
describe("cd-tokens.generated.css (vendored, never edited)", () => {
|
|
70
|
+
it("starts with the generated-file marker naming the brand version", () => {
|
|
71
|
+
expect(vendored.startsWith(MARKER)).toBe(true)
|
|
72
|
+
})
|
|
73
|
+
|
|
74
|
+
it("is the upstream file byte for byte below the marker (pinned hash)", () => {
|
|
75
|
+
const hash = createHash("sha256").update(upstreamPart, "utf8").digest("hex")
|
|
76
|
+
expect(hash, "re-vendor from the skill instead of editing the copy").toBe(UPSTREAM_SHA256)
|
|
77
|
+
})
|
|
78
|
+
|
|
79
|
+
it("is byte-identical to the skill's file when a plugin checkout is reachable", () => {
|
|
80
|
+
const upstream = findUpstream()
|
|
81
|
+
// Off-machine (CI) the pinned hash above is the guard; say so loudly.
|
|
82
|
+
if (!upstream) {
|
|
83
|
+
console.warn(
|
|
84
|
+
`cd-tokens drift: no miragon-brand ${CD_TOKENS_VERSION} checkout found — relying on the pinned hash`,
|
|
85
|
+
)
|
|
86
|
+
return
|
|
87
|
+
}
|
|
88
|
+
expect(upstreamPart).toBe(readFileSync(upstream, "utf8"))
|
|
89
|
+
})
|
|
90
|
+
})
|
|
91
|
+
|
|
92
|
+
describe("CD_TOKENS (the TS mirror of :root)", () => {
|
|
93
|
+
const css = cssTokens(upstreamPart)
|
|
94
|
+
|
|
95
|
+
it("mirrors every --cd-* token value exactly", () => {
|
|
96
|
+
for (const [name, value] of Object.entries(css)) {
|
|
97
|
+
expect(CD_TOKENS[name as keyof typeof CD_TOKENS], `--cd-${name}`).toBe(value)
|
|
98
|
+
}
|
|
99
|
+
})
|
|
100
|
+
|
|
101
|
+
it("declares no token the CSS does not", () => {
|
|
102
|
+
expect(Object.keys(CD_TOKENS).sort()).toEqual(Object.keys(css).sort())
|
|
103
|
+
})
|
|
104
|
+
|
|
105
|
+
it("parses a non-trivial token set (the parser itself is alive)", () => {
|
|
106
|
+
expect(Object.keys(css).length).toBeGreaterThanOrEqual(40)
|
|
107
|
+
expect(css.blau).toBe("#335DE5")
|
|
108
|
+
})
|
|
109
|
+
})
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The Miragon corporate-design tokens (`--cd-*`) as plain TypeScript, for code
|
|
3
|
+
* that cannot read CSS variables — an SVG or canvas renderer (BPMN overlays,
|
|
4
|
+
* chart marks), a server-side image, a test. Keys are the CSS names without the
|
|
5
|
+
* `--cd-` prefix.
|
|
6
|
+
*
|
|
7
|
+
* The source of truth is the vendored `cd-tokens.generated.css` next to this
|
|
8
|
+
* file (miragon-brand 1.8.0, copied unchanged from Miragon/corporate-identity).
|
|
9
|
+
* This module mirrors it value for value; `cd-tokens.test.ts` fails on any
|
|
10
|
+
* drift (modeler-tool-design §13). Never edit a value here without re-vendoring
|
|
11
|
+
* the CSS first.
|
|
12
|
+
*
|
|
13
|
+
* UI code styles through the role tokens (`bg-primary`, `text-link`,
|
|
14
|
+
* `border-danger`, …), never through these constants.
|
|
15
|
+
*/
|
|
16
|
+
export const CD_TOKENS = {
|
|
17
|
+
blau: "#335DE5",
|
|
18
|
+
gruen: "#00E676",
|
|
19
|
+
grau: "#F9F7F7",
|
|
20
|
+
schwarz: "#1D1D1D",
|
|
21
|
+
weiss: "#FFFFFF",
|
|
22
|
+
"blau-link": "#2B50D4",
|
|
23
|
+
"blau-hell": "#6B8AFF",
|
|
24
|
+
success: "#00E676",
|
|
25
|
+
"success-soft": "#DAFBEB",
|
|
26
|
+
"success-hell": "#00E676",
|
|
27
|
+
warning: "#FFB000",
|
|
28
|
+
"warning-soft": "#FFF1D2",
|
|
29
|
+
"warning-hell": "#FFB000",
|
|
30
|
+
danger: "#CD1839",
|
|
31
|
+
"danger-soft": "#FBEEF0",
|
|
32
|
+
"danger-hell": "#FB6D73",
|
|
33
|
+
info: "#335DE5",
|
|
34
|
+
"info-soft": "#EEF1FD",
|
|
35
|
+
"info-hell": "#6B8AFF",
|
|
36
|
+
linie: "#E6E2E2",
|
|
37
|
+
kontur: "#8F8A8A",
|
|
38
|
+
"text-leise": "#6B6666",
|
|
39
|
+
"gradient-brand": "linear-gradient(120deg, #335DE5 30%, #00E676)",
|
|
40
|
+
"gradient-format": "linear-gradient(135deg, #335DE5 0%, #00E676 140%)",
|
|
41
|
+
"space-1": "4px",
|
|
42
|
+
"space-2": "8px",
|
|
43
|
+
"space-3": "16px",
|
|
44
|
+
"space-4": "24px",
|
|
45
|
+
"space-5": "32px",
|
|
46
|
+
"space-6": "48px",
|
|
47
|
+
"space-7": "64px",
|
|
48
|
+
"space-8": "96px",
|
|
49
|
+
"radius-sm": "6px",
|
|
50
|
+
"radius-md": "12px",
|
|
51
|
+
"radius-lg": "16px",
|
|
52
|
+
"radius-pill": "999px",
|
|
53
|
+
"shadow-1": "0 1px 2px rgba(29, 29, 29, 0.06), 0 1px 3px rgba(29, 29, 29, 0.10)",
|
|
54
|
+
"shadow-2": "0 4px 12px rgba(29, 29, 29, 0.10)",
|
|
55
|
+
"shadow-3": "0 12px 32px rgba(29, 29, 29, 0.16)",
|
|
56
|
+
"motion-fast": "150ms",
|
|
57
|
+
"motion-base": "250ms",
|
|
58
|
+
"motion-slow": "400ms",
|
|
59
|
+
ease: "cubic-bezier(0.4, 0, 0.2, 1)",
|
|
60
|
+
"ease-out": "cubic-bezier(0, 0, 0.2, 1)",
|
|
61
|
+
} as const
|
|
62
|
+
|
|
63
|
+
/** A key of {@link CD_TOKENS} — the `--cd-*` name without its prefix. */
|
|
64
|
+
export type CdTokenName = keyof typeof CD_TOKENS
|
|
65
|
+
|
|
66
|
+
/** The miragon-brand release the vendored tokens come from. */
|
|
67
|
+
export const CD_TOKENS_VERSION = "1.8.0"
|