@scaffold-ui-kit/preview 0.0.0-stage → 2.3.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/LICENSE +21 -0
- package/README.md +1868 -2
- package/application/host/bootstrap.ts +43 -0
- package/application/host/main.ts +31 -0
- package/application/host/shell-host.ts +47 -0
- package/application/index.html +12 -0
- package/application/lib/base-url.ts +15 -0
- package/application/lib/no-code-block.ts +7 -0
- package/application/lib/no-setup.ts +3 -0
- package/application/lib/no-views.ts +6 -0
- package/application/preview/code/code.html +12 -0
- package/application/preview/code/main.ts +89 -0
- package/application/preview/globals.ts +254 -0
- package/application/preview/html/main.ts +93 -0
- package/application/preview/html/preview.html +12 -0
- package/application/preview/react/main.tsx +146 -0
- package/application/preview/react/preview.html +12 -0
- package/application/preview/svelte/Preview.svelte +104 -0
- package/application/preview/svelte/main.ts +13 -0
- package/application/preview/svelte/preview.html +12 -0
- package/application/preview/svelte/story-props.ts +172 -0
- package/application/preview/view/main.ts +124 -0
- package/application/preview/view/view.html +12 -0
- package/application/preview/vue/main.ts +145 -0
- package/application/preview/vue/preview.html +12 -0
- package/application/shells/charcell/components/Application/index.css +37 -0
- package/application/shells/charcell/components/Application/index.tsx +65 -0
- package/application/shells/charcell/components/Bar/index.css +68 -0
- package/application/shells/charcell/components/Bar/index.tsx +60 -0
- package/application/shells/charcell/components/CodePane/index.css +60 -0
- package/application/shells/charcell/components/CodePane/index.tsx +113 -0
- package/application/shells/charcell/components/ComponentStage/index.css +26 -0
- package/application/shells/charcell/components/ComponentStage/index.tsx +110 -0
- package/application/shells/charcell/components/Control/index.css +20 -0
- package/application/shells/charcell/components/Control/index.tsx +118 -0
- package/application/shells/charcell/components/CopyLink/index.tsx +35 -0
- package/application/shells/charcell/components/Description/index.css +6 -0
- package/application/shells/charcell/components/Description/index.tsx +24 -0
- package/application/shells/charcell/components/EditorAddDialog/index.css +9 -0
- package/application/shells/charcell/components/EditorAddDialog/index.tsx +158 -0
- package/application/shells/charcell/components/EditorPanel/index.css +48 -0
- package/application/shells/charcell/components/EditorPanel/index.tsx +496 -0
- package/application/shells/charcell/components/EventsRow/index.css +42 -0
- package/application/shells/charcell/components/EventsRow/index.tsx +68 -0
- package/application/shells/charcell/components/HeadingRow/index.css +11 -0
- package/application/shells/charcell/components/HeadingRow/index.tsx +16 -0
- package/application/shells/charcell/components/Hint/index.css +16 -0
- package/application/shells/charcell/components/Hint/index.tsx +81 -0
- package/application/shells/charcell/components/HtmlWarnings/index.tsx +45 -0
- package/application/shells/charcell/components/KeyHints/index.css +27 -0
- package/application/shells/charcell/components/KeyHints/index.tsx +106 -0
- package/application/shells/charcell/components/KitCodeBlock/index.css +55 -0
- package/application/shells/charcell/components/KitCodeBlock/index.tsx +18 -0
- package/application/shells/charcell/components/Markdown/index.tsx +16 -0
- package/application/shells/charcell/components/Navigation/index.css +13 -0
- package/application/shells/charcell/components/Navigation/index.tsx +98 -0
- package/application/shells/charcell/components/NavigationSplit/index.css +16 -0
- package/application/shells/charcell/components/NavigationSplit/index.tsx +82 -0
- package/application/shells/charcell/components/OptionControls/index.tsx +93 -0
- package/application/shells/charcell/components/PaneStatus/index.css +7 -0
- package/application/shells/charcell/components/PaneStatus/index.tsx +47 -0
- package/application/shells/charcell/components/PaneWidth/index.tsx +45 -0
- package/application/shells/charcell/components/PreviewGrid/index.css +39 -0
- package/application/shells/charcell/components/PreviewGrid/index.tsx +344 -0
- package/application/shells/charcell/components/PreviewPane/index.css +127 -0
- package/application/shells/charcell/components/PreviewPane/index.tsx +182 -0
- package/application/shells/charcell/components/PromptBar/index.tsx +133 -0
- package/application/shells/charcell/components/ScenarioRow/index.css +36 -0
- package/application/shells/charcell/components/ScenarioRow/index.tsx +71 -0
- package/application/shells/charcell/components/Select/index.tsx +48 -0
- package/application/shells/charcell/components/SlotOutlet/index.css +7 -0
- package/application/shells/charcell/components/SlotOutlet/index.tsx +25 -0
- package/application/shells/charcell/components/StageBar/index.css +7 -0
- package/application/shells/charcell/components/StageBar/index.tsx +109 -0
- package/application/shells/charcell/components/StageSplit/index.css +11 -0
- package/application/shells/charcell/components/StageSplit/index.tsx +99 -0
- package/application/shells/charcell/components/StatusBar/index.tsx +30 -0
- package/application/shells/charcell/components/ViewControls/index.css +15 -0
- package/application/shells/charcell/components/ViewControls/index.tsx +58 -0
- package/application/shells/charcell/components/ViewHeading/index.css +13 -0
- package/application/shells/charcell/components/ViewHeading/index.tsx +8 -0
- package/application/shells/charcell/components/ViewStage/index.css +9 -0
- package/application/shells/charcell/components/ViewStage/index.tsx +25 -0
- package/application/shells/charcell/components/WrapToggle/index.tsx +27 -0
- package/application/shells/charcell/configuration.ts +45 -0
- package/application/shells/charcell/controller-context.ts +27 -0
- package/application/shells/charcell/fit-labels.ts +42 -0
- package/application/shells/charcell/html-warnings.ts +18 -0
- package/application/shells/charcell/index.tsx +82 -0
- package/application/shells/charcell/page-loading.html +57 -0
- package/application/shells/charcell/placement.ts +24 -0
- package/application/shells/charcell/shell-options.ts +23 -0
- package/application/shells/charcell/shell.css +37 -0
- package/application/shells/charcell/shell.tsx +25 -0
- package/application/shells/charcell/split-reset.ts +47 -0
- package/application/shells/charcell/stacked-rows.ts +117 -0
- package/application/shells/charcell/stage-toggles.ts +93 -0
- package/application/types/manifest.d.ts +6 -0
- package/application/types/preview-configuration.d.ts +10 -0
- package/application/types/preview-shell.d.ts +7 -0
- package/application/types/react-registry.d.ts +15 -0
- package/application/types/vue-registry.d.ts +6 -0
- package/dist/build.d.ts +24 -0
- package/dist/build.js +34 -0
- package/dist/check.d.ts +48 -0
- package/dist/check.js +781 -0
- package/dist/cli.d.ts +2 -0
- package/dist/cli.js +88 -0
- package/dist/context.d.ts +179 -0
- package/dist/context.js +783 -0
- package/dist/controller/catalog.d.ts +339 -0
- package/dist/controller/catalog.js +367 -0
- package/dist/controller/create-preview-controller.d.ts +532 -0
- package/dist/controller/create-preview-controller.js +1707 -0
- package/dist/controller/editor-tree.d.ts +161 -0
- package/dist/controller/editor-tree.js +373 -0
- package/dist/controller/html-source.d.ts +62 -0
- package/dist/controller/html-source.js +61 -0
- package/dist/controller/index.d.ts +9 -0
- package/dist/controller/index.js +12 -0
- package/dist/controller/persistence.d.ts +191 -0
- package/dist/controller/persistence.js +315 -0
- package/dist/controller/regeneration.d.ts +30 -0
- package/dist/controller/regeneration.js +27 -0
- package/dist/controller/source.d.ts +80 -0
- package/dist/controller/source.js +236 -0
- package/dist/controller/store.d.ts +27 -0
- package/dist/controller/store.js +40 -0
- package/dist/declarations/application/shells/charcell/components/Application/index.d.ts +2 -0
- package/dist/declarations/application/shells/charcell/components/Bar/index.d.ts +11 -0
- package/dist/declarations/application/shells/charcell/components/CodePane/index.d.ts +5 -0
- package/dist/declarations/application/shells/charcell/components/ComponentStage/index.d.ts +2 -0
- package/dist/declarations/application/shells/charcell/components/Control/index.d.ts +9 -0
- package/dist/declarations/application/shells/charcell/components/CopyLink/index.d.ts +1 -0
- package/dist/declarations/application/shells/charcell/components/Description/index.d.ts +5 -0
- package/dist/declarations/application/shells/charcell/components/EditorAddDialog/index.d.ts +6 -0
- package/dist/declarations/application/shells/charcell/components/EditorPanel/index.d.ts +2 -0
- package/dist/declarations/application/shells/charcell/components/EventsRow/index.d.ts +4 -0
- package/dist/declarations/application/shells/charcell/components/HeadingRow/index.d.ts +6 -0
- package/dist/declarations/application/shells/charcell/components/Hint/index.d.ts +11 -0
- package/dist/declarations/application/shells/charcell/components/HtmlWarnings/index.d.ts +5 -0
- package/dist/declarations/application/shells/charcell/components/KeyHints/index.d.ts +2 -0
- package/dist/declarations/application/shells/charcell/components/KitCodeBlock/index.d.ts +5 -0
- package/dist/declarations/application/shells/charcell/components/Markdown/index.d.ts +3 -0
- package/dist/declarations/application/shells/charcell/components/Navigation/index.d.ts +8 -0
- package/dist/declarations/application/shells/charcell/components/NavigationSplit/index.d.ts +7 -0
- package/dist/declarations/application/shells/charcell/components/OptionControls/index.d.ts +7 -0
- package/dist/declarations/application/shells/charcell/components/PaneStatus/index.d.ts +2 -0
- package/dist/declarations/application/shells/charcell/components/PaneWidth/index.d.ts +4 -0
- package/dist/declarations/application/shells/charcell/components/PreviewGrid/index.d.ts +7 -0
- package/dist/declarations/application/shells/charcell/components/PreviewPane/index.d.ts +9 -0
- package/dist/declarations/application/shells/charcell/components/PromptBar/index.d.ts +1 -0
- package/dist/declarations/application/shells/charcell/components/ScenarioRow/index.d.ts +2 -0
- package/dist/declarations/application/shells/charcell/components/Select/index.d.ts +16 -0
- package/dist/declarations/application/shells/charcell/components/SlotOutlet/index.d.ts +5 -0
- package/dist/declarations/application/shells/charcell/components/StageBar/index.d.ts +2 -0
- package/dist/declarations/application/shells/charcell/components/StageSplit/index.d.ts +17 -0
- package/dist/declarations/application/shells/charcell/components/StatusBar/index.d.ts +1 -0
- package/dist/declarations/application/shells/charcell/components/ViewControls/index.d.ts +9 -0
- package/dist/declarations/application/shells/charcell/components/ViewHeading/index.d.ts +4 -0
- package/dist/declarations/application/shells/charcell/components/ViewStage/index.d.ts +4 -0
- package/dist/declarations/application/shells/charcell/components/WrapToggle/index.d.ts +1 -0
- package/dist/declarations/application/shells/charcell/configuration.d.ts +31 -0
- package/dist/declarations/application/shells/charcell/controller-context.d.ts +9 -0
- package/dist/declarations/application/shells/charcell/fit-labels.d.ts +18 -0
- package/dist/declarations/application/shells/charcell/html-warnings.d.ts +5 -0
- package/dist/declarations/application/shells/charcell/index.d.ts +39 -0
- package/dist/declarations/application/shells/charcell/placement.d.ts +7 -0
- package/dist/declarations/application/shells/charcell/shell-options.d.ts +15 -0
- package/dist/declarations/application/shells/charcell/shell.d.ts +9 -0
- package/dist/declarations/application/shells/charcell/split-reset.d.ts +30 -0
- package/dist/declarations/application/shells/charcell/stacked-rows.d.ts +58 -0
- package/dist/declarations/application/shells/charcell/stage-toggles.d.ts +28 -0
- package/dist/declarations/src/controller/catalog.d.ts +339 -0
- package/dist/declarations/src/controller/create-preview-controller.d.ts +532 -0
- package/dist/declarations/src/controller/editor-tree.d.ts +161 -0
- package/dist/declarations/src/controller/html-source.d.ts +62 -0
- package/dist/declarations/src/controller/index.d.ts +9 -0
- package/dist/declarations/src/controller/persistence.d.ts +191 -0
- package/dist/declarations/src/controller/regeneration.d.ts +30 -0
- package/dist/declarations/src/controller/source.d.ts +80 -0
- package/dist/declarations/src/controller/store.d.ts +27 -0
- package/dist/declarations/src/emit/common.d.ts +103 -0
- package/dist/declarations/src/emit/manifest.d.ts +138 -0
- package/dist/declarations/src/emit/source.d.ts +87 -0
- package/dist/declarations/src/lib/jsx-roots.d.ts +22 -0
- package/dist/declarations/src/lib/module-of-source.d.ts +18 -0
- package/dist/declarations/src/lib/naming.d.ts +29 -0
- package/dist/declarations/src/lib/react-spelling.d.ts +68 -0
- package/dist/declarations/src/lib/scenario-story.d.ts +41 -0
- package/dist/declarations/src/lib/slot-fill.d.ts +15 -0
- package/dist/declarations/src/lib/types.d.ts +741 -0
- package/dist/declarations/src/options.d.ts +224 -0
- package/dist/declarations/src/protocol.d.ts +541 -0
- package/dist/declarations/src/react-view.d.ts +22 -0
- package/dist/declarations/src/react.d.ts +17 -0
- package/dist/declarations/src/shell.d.ts +99 -0
- package/dist/declarations/src/views.d.ts +152 -0
- package/dist/development-server.d.ts +121 -0
- package/dist/development-server.js +331 -0
- package/dist/emit/common.d.ts +103 -0
- package/dist/emit/common.js +170 -0
- package/dist/emit/html-source.d.ts +46 -0
- package/dist/emit/html-source.js +322 -0
- package/dist/emit/manifest.d.ts +138 -0
- package/dist/emit/manifest.js +74 -0
- package/dist/emit/react.d.ts +16 -0
- package/dist/emit/react.js +210 -0
- package/dist/emit/scratch.d.ts +40 -0
- package/dist/emit/scratch.js +116 -0
- package/dist/emit/source.d.ts +87 -0
- package/dist/emit/source.js +789 -0
- package/dist/emit/svelte.d.ts +9 -0
- package/dist/emit/svelte.js +177 -0
- package/dist/emit/vue.d.ts +2 -0
- package/dist/emit/vue.js +152 -0
- package/dist/enumerate.d.ts +2 -0
- package/dist/enumerate.js +162 -0
- package/dist/generate.d.ts +43 -0
- package/dist/generate.js +302 -0
- package/dist/html-stylesheet.d.ts +43 -0
- package/dist/html-stylesheet.js +145 -0
- package/dist/index.d.ts +18 -0
- package/dist/index.js +21 -0
- package/dist/landing.d.ts +16 -0
- package/dist/landing.js +45 -0
- package/dist/lib/exported-types.d.ts +42 -0
- package/dist/lib/exported-types.js +86 -0
- package/dist/lib/html-attributes.d.ts +2 -0
- package/dist/lib/html-attributes.js +111 -0
- package/dist/lib/html-warnings.d.ts +19 -0
- package/dist/lib/html-warnings.js +79 -0
- package/dist/lib/jsx-roots.d.ts +22 -0
- package/dist/lib/jsx-roots.js +243 -0
- package/dist/lib/module-of-source.d.ts +18 -0
- package/dist/lib/module-of-source.js +24 -0
- package/dist/lib/naming.d.ts +29 -0
- package/dist/lib/naming.js +56 -0
- package/dist/lib/parse-type.d.ts +32 -0
- package/dist/lib/parse-type.js +103 -0
- package/dist/lib/react-spelling.d.ts +68 -0
- package/dist/lib/react-spelling.js +197 -0
- package/dist/lib/scenario-story.d.ts +41 -0
- package/dist/lib/scenario-story.js +84 -0
- package/dist/lib/slot-fill.d.ts +15 -0
- package/dist/lib/slot-fill.js +92 -0
- package/dist/lib/template-files.d.ts +14 -0
- package/dist/lib/template-files.js +25 -0
- package/dist/lib/types.d.ts +741 -0
- package/dist/lib/types.js +13 -0
- package/dist/lib/void-elements.d.ts +7 -0
- package/dist/lib/void-elements.js +13 -0
- package/dist/load.d.ts +37 -0
- package/dist/load.js +82 -0
- package/dist/model.d.ts +44 -0
- package/dist/model.js +464 -0
- package/dist/options.d.ts +224 -0
- package/dist/options.js +223 -0
- package/dist/prop-types.d.ts +26 -0
- package/dist/prop-types.js +102 -0
- package/dist/props-from.d.ts +84 -0
- package/dist/props-from.js +510 -0
- package/dist/protocol.d.ts +541 -0
- package/dist/protocol.js +819 -0
- package/dist/react-view.d.ts +22 -0
- package/dist/react-view.js +36 -0
- package/dist/react.d.ts +17 -0
- package/dist/react.js +23 -0
- package/dist/sass-importers.d.ts +26 -0
- package/dist/sass-importers.js +32 -0
- package/dist/shell-acceptance.d.ts +21 -0
- package/dist/shell-acceptance.js +37 -0
- package/dist/shell-page.d.ts +36 -0
- package/dist/shell-page.js +90 -0
- package/dist/shell-peers.d.ts +38 -0
- package/dist/shell-peers.js +61 -0
- package/dist/shell.d.ts +99 -0
- package/dist/shell.js +52 -0
- package/dist/shells/charcell/page.d.ts +8 -0
- package/dist/shells/charcell/page.js +69 -0
- package/dist/story-source.d.ts +113 -0
- package/dist/story-source.js +271 -0
- package/dist/story.d.ts +5 -0
- package/dist/story.js +28 -0
- package/dist/testing.d.ts +218 -0
- package/dist/testing.js +284 -0
- package/dist/views.d.ts +152 -0
- package/dist/views.js +7 -0
- package/dist/vite-configuration.d.ts +114 -0
- package/dist/vite-configuration.js +578 -0
- package/package.json +123 -3
- package/src/build.ts +51 -0
- package/src/check.ts +1062 -0
- package/src/cli.ts +123 -0
- package/src/context.ts +1168 -0
- package/src/controller/catalog.ts +719 -0
- package/src/controller/create-preview-controller.ts +2683 -0
- package/src/controller/editor-tree.ts +530 -0
- package/src/controller/html-source.ts +114 -0
- package/src/controller/index.ts +105 -0
- package/src/controller/persistence.ts +403 -0
- package/src/controller/regeneration.ts +55 -0
- package/src/controller/source.ts +333 -0
- package/src/controller/store.ts +55 -0
- package/src/development-server.ts +442 -0
- package/src/emit/common.ts +201 -0
- package/src/emit/html-source.ts +402 -0
- package/src/emit/manifest.ts +241 -0
- package/src/emit/react.ts +263 -0
- package/src/emit/scratch.ts +175 -0
- package/src/emit/source.ts +1094 -0
- package/src/emit/svelte.ts +230 -0
- package/src/emit/vue.ts +194 -0
- package/src/enumerate.ts +220 -0
- package/src/generate.ts +443 -0
- package/src/html-stylesheet.ts +173 -0
- package/src/index.ts +60 -0
- package/src/landing.ts +58 -0
- package/src/lib/exported-types.ts +114 -0
- package/src/lib/html-attributes.ts +113 -0
- package/src/lib/html-warnings.ts +81 -0
- package/src/lib/jsx-roots.ts +238 -0
- package/src/lib/module-of-source.ts +26 -0
- package/src/lib/naming.ts +65 -0
- package/src/lib/parse-type.ts +143 -0
- package/src/lib/react-spelling.ts +235 -0
- package/src/lib/scenario-story.ts +97 -0
- package/src/lib/slot-fill.ts +102 -0
- package/src/lib/template-files.ts +31 -0
- package/src/lib/types.ts +778 -0
- package/src/lib/void-elements.ts +15 -0
- package/src/load.ts +144 -0
- package/src/model.ts +568 -0
- package/src/options.ts +435 -0
- package/src/prop-types.ts +133 -0
- package/src/props-from.ts +678 -0
- package/src/protocol.ts +1135 -0
- package/src/react-view.ts +45 -0
- package/src/react.ts +34 -0
- package/src/sass-importers.ts +45 -0
- package/src/shell-acceptance.ts +45 -0
- package/src/shell-page.ts +133 -0
- package/src/shell-peers.ts +70 -0
- package/src/shell.ts +194 -0
- package/src/shells/charcell/page.ts +82 -0
- package/src/story-source.ts +391 -0
- package/src/story.ts +42 -0
- package/src/testing.ts +497 -0
- package/src/views.ts +183 -0
- package/src/vite-configuration.ts +675 -0
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
// The type names a component's generated module exports, which the kit's
|
|
2
|
+
// package entry re-exports with everything else the module exports: the
|
|
3
|
+
// exported declarations among a template's module-scope lines, as each
|
|
4
|
+
// target places them. Browser-safe.
|
|
5
|
+
const IDENTIFIER = '[A-Za-z_$][\\w$]*';
|
|
6
|
+
/** A declaration that names a type: `export interface X`, `export type X =`,
|
|
7
|
+
* `export enum X`, `export class X` (each with `declare` or `abstract`). */
|
|
8
|
+
const TYPE_DECLARATION = new RegExp(`^\\s*export\\s+(?:declare\\s+)?(?:(?:abstract\\s+)?class|interface|type|(?:const\\s+)?enum)\\s+(${IDENTIFIER})`);
|
|
9
|
+
/** An export list: `export { A, B as C }` or `export type { A } from '...'`. */
|
|
10
|
+
const EXPORT_LIST = /^\s*export\s+(type\s+)?\{([^}]*)\}/;
|
|
11
|
+
/**
|
|
12
|
+
* The type names one module-scope line exports. A value-only export list
|
|
13
|
+
* (`export { a }`) names no type unless a member is marked `type`, as a value
|
|
14
|
+
* cannot be told from a type there.
|
|
15
|
+
*
|
|
16
|
+
* @param line - A verbatim module-scope line.
|
|
17
|
+
* @returns The type names it exports, in order.
|
|
18
|
+
*/
|
|
19
|
+
export function exportedTypeNamesOf(line) {
|
|
20
|
+
const declaration = TYPE_DECLARATION.exec(line);
|
|
21
|
+
if (declaration)
|
|
22
|
+
return [declaration[1]];
|
|
23
|
+
const list = EXPORT_LIST.exec(line);
|
|
24
|
+
if (!list)
|
|
25
|
+
return [];
|
|
26
|
+
const typeOnly = list[1] !== undefined;
|
|
27
|
+
return list[2]
|
|
28
|
+
.split(',')
|
|
29
|
+
.map((member) => member.trim())
|
|
30
|
+
.filter((member) => member !== '' && (typeOnly || /^type\s/.test(member)))
|
|
31
|
+
.map((member) => member
|
|
32
|
+
.replace(/^type\s+/, '')
|
|
33
|
+
.split(/\s+as\s+/)
|
|
34
|
+
.pop()
|
|
35
|
+
.trim())
|
|
36
|
+
.filter((name) => new RegExp(`^${IDENTIFIER}$`).test(name));
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* The type names a template's generated module exports in one scripted
|
|
40
|
+
* target: those its module-scope lines declare, the target's own `imports`
|
|
41
|
+
* merged in (or in their place, with `importsStrategy: 'replace'`).
|
|
42
|
+
*
|
|
43
|
+
* @param template - The component's template.
|
|
44
|
+
* @param target - The scripted target.
|
|
45
|
+
* @returns The exported type names, each once.
|
|
46
|
+
* @example
|
|
47
|
+
* ```ts
|
|
48
|
+
* exportedTypeNames({ imports: ['export interface DateValue { day: string }'] }, 'react');
|
|
49
|
+
* // ['DateValue']
|
|
50
|
+
* ```
|
|
51
|
+
*/
|
|
52
|
+
export function exportedTypeNames(template, target) {
|
|
53
|
+
const override = template.extensions?.[target];
|
|
54
|
+
const own = Array.isArray(override?.imports)
|
|
55
|
+
? override.imports.filter((line) => typeof line === 'string')
|
|
56
|
+
: undefined;
|
|
57
|
+
const lines = own === undefined
|
|
58
|
+
? (template.imports ?? [])
|
|
59
|
+
: override?.importsStrategy === 'replace'
|
|
60
|
+
? own
|
|
61
|
+
: [...(template.imports ?? []), ...own];
|
|
62
|
+
return [
|
|
63
|
+
...new Set(lines.flatMap((entry) => entry.split('\n').flatMap(exportedTypeNamesOf))),
|
|
64
|
+
];
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* The type names a component's generated module exports, per scripted
|
|
68
|
+
* target: none for a component written by hand, whose module the preview
|
|
69
|
+
* does not read.
|
|
70
|
+
*
|
|
71
|
+
* @param component - The component, with the template it was read from.
|
|
72
|
+
* @param targets - The scripted targets the kit builds.
|
|
73
|
+
* @returns The names per target that exports any, or `undefined` when none does.
|
|
74
|
+
*/
|
|
75
|
+
export function exportedTypesOf(component, targets) {
|
|
76
|
+
const template = component.template;
|
|
77
|
+
if (!template || typeof template !== 'object' || Array.isArray(template))
|
|
78
|
+
return undefined;
|
|
79
|
+
const types = {};
|
|
80
|
+
for (const target of targets) {
|
|
81
|
+
const names = exportedTypeNames(template, target);
|
|
82
|
+
if (names.length > 0)
|
|
83
|
+
types[target] = names;
|
|
84
|
+
}
|
|
85
|
+
return Object.keys(types).length > 0 ? types : undefined;
|
|
86
|
+
}
|
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
// Native attribute names a passthrough component forwards to its root element,
|
|
2
|
+
// so a story file may set them beside the declared props. The global attributes
|
|
3
|
+
// plus those of the elements a passthrough root usually is (form controls,
|
|
4
|
+
// links, media, tables); `aria-*` and `data-*` are matched by prefix. Spelled
|
|
5
|
+
// as in HTML, the form a story file's value reaches every target in.
|
|
6
|
+
const HTML_ATTRIBUTES = new Set([
|
|
7
|
+
// global
|
|
8
|
+
'accesskey',
|
|
9
|
+
'autocapitalize',
|
|
10
|
+
'autofocus',
|
|
11
|
+
'class',
|
|
12
|
+
'contenteditable',
|
|
13
|
+
'dir',
|
|
14
|
+
'draggable',
|
|
15
|
+
'enterkeyhint',
|
|
16
|
+
'hidden',
|
|
17
|
+
'id',
|
|
18
|
+
'inert',
|
|
19
|
+
'inputmode',
|
|
20
|
+
'is',
|
|
21
|
+
'lang',
|
|
22
|
+
'nonce',
|
|
23
|
+
'part',
|
|
24
|
+
'popover',
|
|
25
|
+
'role',
|
|
26
|
+
'slot',
|
|
27
|
+
'spellcheck',
|
|
28
|
+
'style',
|
|
29
|
+
'tabindex',
|
|
30
|
+
'title',
|
|
31
|
+
'translate',
|
|
32
|
+
// forms
|
|
33
|
+
'accept',
|
|
34
|
+
'action',
|
|
35
|
+
'autocomplete',
|
|
36
|
+
'checked',
|
|
37
|
+
'cols',
|
|
38
|
+
'dirname',
|
|
39
|
+
'disabled',
|
|
40
|
+
'enctype',
|
|
41
|
+
'for',
|
|
42
|
+
'form',
|
|
43
|
+
'formaction',
|
|
44
|
+
'formenctype',
|
|
45
|
+
'formmethod',
|
|
46
|
+
'formnovalidate',
|
|
47
|
+
'formtarget',
|
|
48
|
+
'list',
|
|
49
|
+
'max',
|
|
50
|
+
'maxlength',
|
|
51
|
+
'method',
|
|
52
|
+
'min',
|
|
53
|
+
'minlength',
|
|
54
|
+
'multiple',
|
|
55
|
+
'name',
|
|
56
|
+
'novalidate',
|
|
57
|
+
'pattern',
|
|
58
|
+
'placeholder',
|
|
59
|
+
'readonly',
|
|
60
|
+
'required',
|
|
61
|
+
'rows',
|
|
62
|
+
'selected',
|
|
63
|
+
'size',
|
|
64
|
+
'step',
|
|
65
|
+
'type',
|
|
66
|
+
'value',
|
|
67
|
+
'wrap',
|
|
68
|
+
'popovertarget',
|
|
69
|
+
'popovertargetaction',
|
|
70
|
+
'label',
|
|
71
|
+
'open',
|
|
72
|
+
// links and media
|
|
73
|
+
'alt',
|
|
74
|
+
'download',
|
|
75
|
+
'height',
|
|
76
|
+
'href',
|
|
77
|
+
'hreflang',
|
|
78
|
+
'loading',
|
|
79
|
+
'media',
|
|
80
|
+
'ping',
|
|
81
|
+
'referrerpolicy',
|
|
82
|
+
'rel',
|
|
83
|
+
'sizes',
|
|
84
|
+
'src',
|
|
85
|
+
'srcset',
|
|
86
|
+
'target',
|
|
87
|
+
'width',
|
|
88
|
+
'decoding',
|
|
89
|
+
'crossorigin',
|
|
90
|
+
'poster',
|
|
91
|
+
'controls',
|
|
92
|
+
'autoplay',
|
|
93
|
+
'loop',
|
|
94
|
+
'muted',
|
|
95
|
+
'playsinline',
|
|
96
|
+
'preload',
|
|
97
|
+
// tables and lists
|
|
98
|
+
'colspan',
|
|
99
|
+
'rowspan',
|
|
100
|
+
'headers',
|
|
101
|
+
'scope',
|
|
102
|
+
'span',
|
|
103
|
+
'reversed',
|
|
104
|
+
'start',
|
|
105
|
+
'datetime',
|
|
106
|
+
'cite',
|
|
107
|
+
]);
|
|
108
|
+
/** Whether `name` is a native HTML attribute a passthrough root forwards. */
|
|
109
|
+
export function isHtmlAttribute(name) {
|
|
110
|
+
return HTML_ATTRIBUTES.has(name) || /^(aria|data)-[a-z0-9-]+$/.test(name);
|
|
111
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Summarizes repeated html warnings: the warnings one component gives for
|
|
3
|
+
* the same reason, such as `baseId is not defined`, become one line counting
|
|
4
|
+
* the expressions, at the place of the first; a warning whose reason no other
|
|
5
|
+
* warning of its component shares stays as it is, as does any warning that
|
|
6
|
+
* is not an expression that could not be evaluated.
|
|
7
|
+
*
|
|
8
|
+
* @param warnings - The warnings, as the render gives them.
|
|
9
|
+
* @returns The warnings, each kind of repeated warning once.
|
|
10
|
+
* @example
|
|
11
|
+
* ```ts
|
|
12
|
+
* summarizeHtmlWarnings([
|
|
13
|
+
* "Tabs: could not evaluate baseId + '-list' (baseId is not defined)",
|
|
14
|
+
* "Tabs: could not evaluate baseId + '-panel' (baseId is not defined)",
|
|
15
|
+
* ]);
|
|
16
|
+
* // ['Tabs: could not evaluate 2 expressions (baseId is not defined)']
|
|
17
|
+
* ```
|
|
18
|
+
*/
|
|
19
|
+
export declare function summarizeHtmlWarnings(warnings: readonly string[]): string[];
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
// What a story's html could not evaluate at rest, summarized for reading: a
|
|
2
|
+
// name that only the component's script defines, such as a per-instance id
|
|
3
|
+
// or its state, fails every expression that reads it, so a component that
|
|
4
|
+
// reads it in several places would otherwise repeat one warning per
|
|
5
|
+
// expression and bury the warnings that differ.
|
|
6
|
+
/** A warning as the render words it: `Name: could not evaluate expression (reason)`. */
|
|
7
|
+
const UNEVALUATED = /^(?:(.+?): )?could not evaluate ([\s\S]+)$/;
|
|
8
|
+
/**
|
|
9
|
+
* Summarizes repeated html warnings: the warnings one component gives for
|
|
10
|
+
* the same reason, such as `baseId is not defined`, become one line counting
|
|
11
|
+
* the expressions, at the place of the first; a warning whose reason no other
|
|
12
|
+
* warning of its component shares stays as it is, as does any warning that
|
|
13
|
+
* is not an expression that could not be evaluated.
|
|
14
|
+
*
|
|
15
|
+
* @param warnings - The warnings, as the render gives them.
|
|
16
|
+
* @returns The warnings, each kind of repeated warning once.
|
|
17
|
+
* @example
|
|
18
|
+
* ```ts
|
|
19
|
+
* summarizeHtmlWarnings([
|
|
20
|
+
* "Tabs: could not evaluate baseId + '-list' (baseId is not defined)",
|
|
21
|
+
* "Tabs: could not evaluate baseId + '-panel' (baseId is not defined)",
|
|
22
|
+
* ]);
|
|
23
|
+
* // ['Tabs: could not evaluate 2 expressions (baseId is not defined)']
|
|
24
|
+
* ```
|
|
25
|
+
*/
|
|
26
|
+
export function summarizeHtmlWarnings(warnings) {
|
|
27
|
+
const groups = new Map();
|
|
28
|
+
const entries = [];
|
|
29
|
+
for (const warning of warnings) {
|
|
30
|
+
const parsed = parseWarning(warning);
|
|
31
|
+
if (parsed === undefined) {
|
|
32
|
+
entries.push(warning);
|
|
33
|
+
continue;
|
|
34
|
+
}
|
|
35
|
+
const key = `${parsed.component ?? ''}\u0000${parsed.reason}`;
|
|
36
|
+
const group = groups.get(key);
|
|
37
|
+
if (group === undefined) {
|
|
38
|
+
groups.set(key, { ...parsed, warnings: [warning] });
|
|
39
|
+
entries.push({ key });
|
|
40
|
+
}
|
|
41
|
+
else if (!group.warnings.includes(warning)) {
|
|
42
|
+
group.warnings.push(warning);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
return entries.map((entry) => {
|
|
46
|
+
if (typeof entry === 'string')
|
|
47
|
+
return entry;
|
|
48
|
+
const group = groups.get(entry.key);
|
|
49
|
+
if (group.warnings.length === 1)
|
|
50
|
+
return group.warnings[0];
|
|
51
|
+
const prefix = group.component === undefined ? '' : `${group.component}: `;
|
|
52
|
+
return `${prefix}could not evaluate ${group.warnings.length} expressions (${group.reason})`;
|
|
53
|
+
});
|
|
54
|
+
}
|
|
55
|
+
/** A warning's component and the reason in its closing parentheses, which
|
|
56
|
+
* may hold parentheses of their own. */
|
|
57
|
+
function parseWarning(warning) {
|
|
58
|
+
const match = UNEVALUATED.exec(warning);
|
|
59
|
+
if (match === null || !warning.endsWith(')'))
|
|
60
|
+
return undefined;
|
|
61
|
+
let depth = 0;
|
|
62
|
+
for (let index = warning.length - 1; index >= 0; index--) {
|
|
63
|
+
const character = warning[index];
|
|
64
|
+
if (character === ')')
|
|
65
|
+
depth++;
|
|
66
|
+
else if (character === '(') {
|
|
67
|
+
depth--;
|
|
68
|
+
if (depth === 0) {
|
|
69
|
+
if (warning[index - 1] !== ' ')
|
|
70
|
+
return undefined;
|
|
71
|
+
const reason = warning.slice(index + 1, -1);
|
|
72
|
+
return match[1] === undefined
|
|
73
|
+
? { reason }
|
|
74
|
+
: { component: match[1], reason };
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
return undefined;
|
|
79
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A React body as one JSX expression: JSX content that is not one already in
|
|
3
|
+
* a fragment, anything else as given.
|
|
4
|
+
*
|
|
5
|
+
* Content opening with a tag goes in a fragment when it has two or more root
|
|
6
|
+
* nodes. Content opening with anything an expression cannot open with - a
|
|
7
|
+
* `{name}` placeholder, punctuation - is text, and goes in one too. Content
|
|
8
|
+
* opening as an expression can (a word, a number, a bracket, a quote) is an
|
|
9
|
+
* expression (`row.name`, `open && <Badge />`) unless it reads as text: two
|
|
10
|
+
* words side by side (`4 messages`), or a word followed by a placeholder or a
|
|
11
|
+
* tag (`hello {name}`, `remove <Button />`). A body the scanner cannot read
|
|
12
|
+
* through is left as given.
|
|
13
|
+
*
|
|
14
|
+
* @param body - The React body, as the fill gives it.
|
|
15
|
+
* @returns The body, in `<>...</>` when it is not one JSX expression.
|
|
16
|
+
* @example
|
|
17
|
+
* singleJsxRoot('<Button label="keep" /><Button label="empty" />');
|
|
18
|
+
* // '<><Button label="keep" /><Button label="empty" /></>'
|
|
19
|
+
* singleJsxRoot('{name}');
|
|
20
|
+
* // '<>{name}</>'
|
|
21
|
+
*/
|
|
22
|
+
export declare function singleJsxRoot(body: string): string;
|
|
@@ -0,0 +1,243 @@
|
|
|
1
|
+
// A React body (a scoped fill's or a part's) is written where JSX takes one
|
|
2
|
+
// expression: an arrow's body, a `return (...)`. Content of two or more root
|
|
3
|
+
// nodes - two sibling elements, an element and text - is no expression there,
|
|
4
|
+
// and neither is text alone (`{name}` after `=>` reads as a block), so each
|
|
5
|
+
// goes in a fragment. Vue and Svelte bodies are markup, which takes them as
|
|
6
|
+
// they are. A plain scanner rather than a parser: the printed source also runs
|
|
7
|
+
// in the browser.
|
|
8
|
+
/** Words that stand before an operand, so a word after them is no text. */
|
|
9
|
+
const PREFIX_KEYWORDS = new Set(['typeof', 'void', 'new', 'await', 'delete']);
|
|
10
|
+
/** Words that stand between operands, so the words beside them are no text. */
|
|
11
|
+
const INFIX_KEYWORDS = new Set(['in', 'instanceof', 'as', 'satisfies']);
|
|
12
|
+
/**
|
|
13
|
+
* A React body as one JSX expression: JSX content that is not one already in
|
|
14
|
+
* a fragment, anything else as given.
|
|
15
|
+
*
|
|
16
|
+
* Content opening with a tag goes in a fragment when it has two or more root
|
|
17
|
+
* nodes. Content opening with anything an expression cannot open with - a
|
|
18
|
+
* `{name}` placeholder, punctuation - is text, and goes in one too. Content
|
|
19
|
+
* opening as an expression can (a word, a number, a bracket, a quote) is an
|
|
20
|
+
* expression (`row.name`, `open && <Badge />`) unless it reads as text: two
|
|
21
|
+
* words side by side (`4 messages`), or a word followed by a placeholder or a
|
|
22
|
+
* tag (`hello {name}`, `remove <Button />`). A body the scanner cannot read
|
|
23
|
+
* through is left as given.
|
|
24
|
+
*
|
|
25
|
+
* @param body - The React body, as the fill gives it.
|
|
26
|
+
* @returns The body, in `<>...</>` when it is not one JSX expression.
|
|
27
|
+
* @example
|
|
28
|
+
* singleJsxRoot('<Button label="keep" /><Button label="empty" />');
|
|
29
|
+
* // '<><Button label="keep" /><Button label="empty" /></>'
|
|
30
|
+
* singleJsxRoot('{name}');
|
|
31
|
+
* // '<>{name}</>'
|
|
32
|
+
*/
|
|
33
|
+
export function singleJsxRoot(body) {
|
|
34
|
+
const trimmed = body.trim();
|
|
35
|
+
if (trimmed === '')
|
|
36
|
+
return body;
|
|
37
|
+
if (trimmed.startsWith('<')) {
|
|
38
|
+
const roots = countRoots(trimmed);
|
|
39
|
+
return roots !== undefined && roots > 1 ? `<>${trimmed}</>` : body;
|
|
40
|
+
}
|
|
41
|
+
const opensExpression = /^[A-Za-z0-9_$([!+\-~.'"`]/.test(trimmed);
|
|
42
|
+
return !opensExpression || readsAsText(trimmed) ? `<>${trimmed}</>` : body;
|
|
43
|
+
}
|
|
44
|
+
/** Whether content that opens as an expression can is text instead: two
|
|
45
|
+
* words side by side, or a word before a placeholder or a tag, outside
|
|
46
|
+
* brackets. */
|
|
47
|
+
function readsAsText(content) {
|
|
48
|
+
let depth = 0;
|
|
49
|
+
// The word last read at the top level, while only whitespace follows it.
|
|
50
|
+
let previousWord;
|
|
51
|
+
let index = 0;
|
|
52
|
+
while (index < content.length) {
|
|
53
|
+
const character = content[index];
|
|
54
|
+
if (character === '"' || character === "'" || character === '`') {
|
|
55
|
+
const end = stringEnd(content, index);
|
|
56
|
+
// A quote that never closes is an apostrophe in text.
|
|
57
|
+
if (end === undefined)
|
|
58
|
+
return true;
|
|
59
|
+
index = end;
|
|
60
|
+
previousWord = undefined;
|
|
61
|
+
continue;
|
|
62
|
+
}
|
|
63
|
+
if (depth === 0) {
|
|
64
|
+
const word = /^[A-Za-z0-9_$]+/.exec(content.slice(index))?.[0];
|
|
65
|
+
if (word) {
|
|
66
|
+
const spaced = index > 0 && /\s/.test(content[index - 1]);
|
|
67
|
+
if (previousWord !== undefined &&
|
|
68
|
+
spaced &&
|
|
69
|
+
!PREFIX_KEYWORDS.has(previousWord) &&
|
|
70
|
+
!INFIX_KEYWORDS.has(previousWord) &&
|
|
71
|
+
!INFIX_KEYWORDS.has(word))
|
|
72
|
+
return true;
|
|
73
|
+
previousWord = word;
|
|
74
|
+
index += word.length;
|
|
75
|
+
continue;
|
|
76
|
+
}
|
|
77
|
+
if (/\s/.test(character)) {
|
|
78
|
+
index++;
|
|
79
|
+
continue;
|
|
80
|
+
}
|
|
81
|
+
if (previousWord !== undefined && character === '{')
|
|
82
|
+
return true;
|
|
83
|
+
if (character === '<' && /[A-Za-z>]/.test(content[index + 1] ?? '')) {
|
|
84
|
+
const elementClose = elementEnd(content, index);
|
|
85
|
+
if (elementClose !== undefined) {
|
|
86
|
+
// A tag after a word is text beside an element; after an operator
|
|
87
|
+
// it is an operand, read past whole.
|
|
88
|
+
if (previousWord !== undefined)
|
|
89
|
+
return true;
|
|
90
|
+
index = elementClose;
|
|
91
|
+
continue;
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
// A word joined to what follows by punctuation (`row.name`) is one
|
|
95
|
+
// expression, not text.
|
|
96
|
+
previousWord = undefined;
|
|
97
|
+
}
|
|
98
|
+
if (character === '(' || character === '[' || character === '{')
|
|
99
|
+
depth++;
|
|
100
|
+
else if (character === ')' || character === ']' || character === '}')
|
|
101
|
+
depth--;
|
|
102
|
+
index++;
|
|
103
|
+
}
|
|
104
|
+
return false;
|
|
105
|
+
}
|
|
106
|
+
/** The root nodes of JSX content, or `undefined` when it does not read through. */
|
|
107
|
+
function countRoots(content) {
|
|
108
|
+
let roots = 0;
|
|
109
|
+
let index = 0;
|
|
110
|
+
while (index < content.length) {
|
|
111
|
+
const character = content[index];
|
|
112
|
+
if (/\s/.test(character)) {
|
|
113
|
+
index++;
|
|
114
|
+
continue;
|
|
115
|
+
}
|
|
116
|
+
const end = character === '<'
|
|
117
|
+
? elementEnd(content, index)
|
|
118
|
+
: character === '{'
|
|
119
|
+
? braceEnd(content, index)
|
|
120
|
+
: textEnd(content, index);
|
|
121
|
+
if (end === undefined)
|
|
122
|
+
return undefined;
|
|
123
|
+
roots++;
|
|
124
|
+
index = end;
|
|
125
|
+
}
|
|
126
|
+
return roots;
|
|
127
|
+
}
|
|
128
|
+
/** The index past a run of text, at the next tag or expression. */
|
|
129
|
+
function textEnd(content, start) {
|
|
130
|
+
let index = start;
|
|
131
|
+
while (index < content.length &&
|
|
132
|
+
content[index] !== '<' &&
|
|
133
|
+
content[index] !== '{')
|
|
134
|
+
index++;
|
|
135
|
+
return index;
|
|
136
|
+
}
|
|
137
|
+
/** The index past the element (or fragment) that opens at `start`. */
|
|
138
|
+
function elementEnd(content, start) {
|
|
139
|
+
let depth = 0;
|
|
140
|
+
let index = start;
|
|
141
|
+
while (index < content.length) {
|
|
142
|
+
const character = content[index];
|
|
143
|
+
if (character === '{') {
|
|
144
|
+
const end = braceEnd(content, index);
|
|
145
|
+
if (end === undefined)
|
|
146
|
+
return undefined;
|
|
147
|
+
index = end;
|
|
148
|
+
continue;
|
|
149
|
+
}
|
|
150
|
+
if (character !== '<') {
|
|
151
|
+
index++;
|
|
152
|
+
continue;
|
|
153
|
+
}
|
|
154
|
+
const closing = content[index + 1] === '/';
|
|
155
|
+
const end = tagEnd(content, index);
|
|
156
|
+
if (end === undefined)
|
|
157
|
+
return undefined;
|
|
158
|
+
const selfClosing = !closing && content[end - 2] === '/';
|
|
159
|
+
if (closing)
|
|
160
|
+
depth--;
|
|
161
|
+
else if (!selfClosing)
|
|
162
|
+
depth++;
|
|
163
|
+
index = end;
|
|
164
|
+
if (depth === 0)
|
|
165
|
+
return index;
|
|
166
|
+
if (depth < 0)
|
|
167
|
+
return undefined;
|
|
168
|
+
}
|
|
169
|
+
return undefined;
|
|
170
|
+
}
|
|
171
|
+
/** The index past a tag's `>`, its attribute strings and expressions skipped. */
|
|
172
|
+
function tagEnd(content, start) {
|
|
173
|
+
let index = start + 1;
|
|
174
|
+
while (index < content.length) {
|
|
175
|
+
const character = content[index];
|
|
176
|
+
if (character === '>')
|
|
177
|
+
return index + 1;
|
|
178
|
+
if (character === '"' || character === "'") {
|
|
179
|
+
const end = content.indexOf(character, index + 1);
|
|
180
|
+
if (end === -1)
|
|
181
|
+
return undefined;
|
|
182
|
+
index = end + 1;
|
|
183
|
+
continue;
|
|
184
|
+
}
|
|
185
|
+
if (character === '{') {
|
|
186
|
+
const end = braceEnd(content, index);
|
|
187
|
+
if (end === undefined)
|
|
188
|
+
return undefined;
|
|
189
|
+
index = end;
|
|
190
|
+
continue;
|
|
191
|
+
}
|
|
192
|
+
index++;
|
|
193
|
+
}
|
|
194
|
+
return undefined;
|
|
195
|
+
}
|
|
196
|
+
/** The index past the `}` that balances the `{` at `start`, strings skipped. */
|
|
197
|
+
function braceEnd(content, start) {
|
|
198
|
+
let depth = 0;
|
|
199
|
+
let index = start;
|
|
200
|
+
while (index < content.length) {
|
|
201
|
+
const character = content[index];
|
|
202
|
+
if (character === '"' || character === "'" || character === '`') {
|
|
203
|
+
const end = stringEnd(content, index);
|
|
204
|
+
if (end === undefined)
|
|
205
|
+
return undefined;
|
|
206
|
+
index = end;
|
|
207
|
+
continue;
|
|
208
|
+
}
|
|
209
|
+
if (character === '{')
|
|
210
|
+
depth++;
|
|
211
|
+
else if (character === '}') {
|
|
212
|
+
depth--;
|
|
213
|
+
if (depth === 0)
|
|
214
|
+
return index + 1;
|
|
215
|
+
}
|
|
216
|
+
index++;
|
|
217
|
+
}
|
|
218
|
+
return undefined;
|
|
219
|
+
}
|
|
220
|
+
/** The index past a string literal opening at `start`, escapes and a template's
|
|
221
|
+
* `${...}` skipped. */
|
|
222
|
+
function stringEnd(content, start) {
|
|
223
|
+
const quote = content[start];
|
|
224
|
+
let index = start + 1;
|
|
225
|
+
while (index < content.length) {
|
|
226
|
+
const character = content[index];
|
|
227
|
+
if (character === '\\') {
|
|
228
|
+
index += 2;
|
|
229
|
+
continue;
|
|
230
|
+
}
|
|
231
|
+
if (character === quote)
|
|
232
|
+
return index + 1;
|
|
233
|
+
if (quote === '`' && character === '$' && content[index + 1] === '{') {
|
|
234
|
+
const end = braceEnd(content, index + 1);
|
|
235
|
+
if (end === undefined)
|
|
236
|
+
return undefined;
|
|
237
|
+
index = end;
|
|
238
|
+
continue;
|
|
239
|
+
}
|
|
240
|
+
index++;
|
|
241
|
+
}
|
|
242
|
+
return undefined;
|
|
243
|
+
}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
/** The token a source's `moduleBase` names its target with. */
|
|
2
|
+
export declare const TARGET_TOKEN = "{target}";
|
|
3
|
+
/**
|
|
4
|
+
* The module a source's components are imported from for one target: the
|
|
5
|
+
* source's `moduleBase` with `{target}` replaced by the target, or, when it
|
|
6
|
+
* has no `{target}`, the target as a subpath of it.
|
|
7
|
+
*
|
|
8
|
+
* @param moduleBase - The source's `moduleBase`.
|
|
9
|
+
* @param target - The target, such as `'react'`.
|
|
10
|
+
* @returns The module specifier.
|
|
11
|
+
* @example
|
|
12
|
+
* ```ts
|
|
13
|
+
* moduleOfSource('my-ui-kit', 'react'); // 'my-ui-kit/react'
|
|
14
|
+
* moduleOfSource('@acme/{target}', 'react'); // '@acme/react'
|
|
15
|
+
* moduleOfSource('acme-{target}', 'vue'); // 'acme-vue'
|
|
16
|
+
* ```
|
|
17
|
+
*/
|
|
18
|
+
export declare function moduleOfSource(moduleBase: string, target: string): string;
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
// The module a source's components are imported from for one target, shared by
|
|
2
|
+
// the generator (Node) and the controller's source printer (browser).
|
|
3
|
+
/** The token a source's `moduleBase` names its target with. */
|
|
4
|
+
export const TARGET_TOKEN = '{target}';
|
|
5
|
+
/**
|
|
6
|
+
* The module a source's components are imported from for one target: the
|
|
7
|
+
* source's `moduleBase` with `{target}` replaced by the target, or, when it
|
|
8
|
+
* has no `{target}`, the target as a subpath of it.
|
|
9
|
+
*
|
|
10
|
+
* @param moduleBase - The source's `moduleBase`.
|
|
11
|
+
* @param target - The target, such as `'react'`.
|
|
12
|
+
* @returns The module specifier.
|
|
13
|
+
* @example
|
|
14
|
+
* ```ts
|
|
15
|
+
* moduleOfSource('my-ui-kit', 'react'); // 'my-ui-kit/react'
|
|
16
|
+
* moduleOfSource('@acme/{target}', 'react'); // '@acme/react'
|
|
17
|
+
* moduleOfSource('acme-{target}', 'vue'); // 'acme-vue'
|
|
18
|
+
* ```
|
|
19
|
+
*/
|
|
20
|
+
export function moduleOfSource(moduleBase, target) {
|
|
21
|
+
return moduleBase.includes(TARGET_TOKEN)
|
|
22
|
+
? moduleBase.split(TARGET_TOKEN).join(target)
|
|
23
|
+
: `${moduleBase}/${target}`;
|
|
24
|
+
}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
export declare function sanitize(value: string): string;
|
|
2
|
+
/** The id of the preview's own Empty scenario, which renders a component
|
|
3
|
+
* with its slots empty: no scenario of a story's takes it. */
|
|
4
|
+
export declare const EMPTY_SCENARIO_ID = "empty";
|
|
5
|
+
/**
|
|
6
|
+
* The id a pane mounts the story of one scenario by, when the scenario has
|
|
7
|
+
* slot content of its own: the component's id and the scenario's, with two
|
|
8
|
+
* hyphens between, which no component id holds.
|
|
9
|
+
*
|
|
10
|
+
* @param componentId - The component's story id.
|
|
11
|
+
* @param scenarioId - The scenario's id.
|
|
12
|
+
* @returns The scenario story's id.
|
|
13
|
+
* @example
|
|
14
|
+
* ```ts
|
|
15
|
+
* scenarioStoryId('components-notice', 'warning'); // 'components-notice--warning'
|
|
16
|
+
* ```
|
|
17
|
+
*/
|
|
18
|
+
export declare function scenarioStoryId(componentId: string, scenarioId: string): string;
|
|
19
|
+
export declare function storyId(title: string, exportName: string): string;
|
|
20
|
+
/**
|
|
21
|
+
* The name a kit's build gives a template without a component node, from its
|
|
22
|
+
* file: the stem's alphanumeric runs in PascalCase, `_` before a leading
|
|
23
|
+
* digit, `Component` when nothing is left (`theme-toggle.ts` → `ThemeToggle`,
|
|
24
|
+
* `2up.grid.ts` → `_2upGrid`). A copy of `componentNameFromFilePath` in
|
|
25
|
+
* scaffold-ui-kit's `template-sources.ts`, the source of truth, which this
|
|
26
|
+
* package cannot import; the two must agree, since the name namespaces the
|
|
27
|
+
* `data-jte-node` markers the kit's stylesheet selects.
|
|
28
|
+
*/
|
|
29
|
+
export declare function componentNameFromFile(file: string): string;
|