@vizejs/vite-plugin-musea 0.32.0 → 0.34.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.
Files changed (63) hide show
  1. package/README.md +7 -7
  2. package/dist/a11y/index.d.mts +2 -0
  3. package/dist/a11y/index.mjs +2 -0
  4. package/dist/{a11y-7maCHrYD.js → a11y-DNCg2qCB.mjs} +16 -24
  5. package/dist/a11y-DNCg2qCB.mjs.map +1 -0
  6. package/dist/autogen/index.d.mts +66 -0
  7. package/dist/autogen/index.d.mts.map +1 -0
  8. package/dist/autogen/index.mjs +2 -0
  9. package/dist/{autogen-dfLosbY_.js → autogen-3-y1d0ou.mjs} +29 -21
  10. package/dist/autogen-3-y1d0ou.mjs.map +1 -0
  11. package/dist/cli/{index.d.ts → index.d.mts} +3 -24
  12. package/dist/cli/index.d.mts.map +1 -0
  13. package/dist/cli/{index.js → index.mjs} +62 -62
  14. package/dist/cli/index.mjs.map +1 -0
  15. package/dist/gallery/assets/{cssMode-B7TGecRV.js → cssMode-cT8muvO_.js} +1 -1
  16. package/dist/gallery/assets/{editor.api-BC1PBCLb.js → editor.api-aFfQJDkw.js} +1 -1
  17. package/dist/gallery/assets/{editor.main-DLQsz_NY.js → editor.main-DMqE48tW.js} +2 -2
  18. package/dist/gallery/assets/{freemarker2-D2ZPJ6qb.js → freemarker2-B6IBKB9r.js} +1 -1
  19. package/dist/gallery/assets/{handlebars-CcyadhwH.js → handlebars-zNX2LtzG.js} +1 -1
  20. package/dist/gallery/assets/{html-q3gp27Kd.js → html-BKYZbazO.js} +1 -1
  21. package/dist/gallery/assets/{htmlMode-T3iVYbeW.js → htmlMode-Bl1BwXnQ.js} +1 -1
  22. package/dist/gallery/assets/index-9OXG8DGI.css +1 -0
  23. package/dist/gallery/assets/{index-Cr99oWYP.js → index-Dltd3znx.js} +5 -5
  24. package/dist/gallery/assets/{javascript-S0QyTjKY.js → javascript-DwBI_Z0J.js} +1 -1
  25. package/dist/gallery/assets/{jsonMode-BIxPM6pZ.js → jsonMode-CBK55pb7.js} +1 -1
  26. package/dist/gallery/assets/{liquid-CNck0h86.js → liquid-D87ggETD.js} +1 -1
  27. package/dist/gallery/assets/{mdx-D6_ZVroO.js → mdx-CBs_aoHd.js} +1 -1
  28. package/dist/gallery/assets/{monaco.contribution-rExTCYiy.js → monaco.contribution-BHYQJQ-0.js} +2 -2
  29. package/dist/gallery/assets/{python-DSEg-0AY.js → python-CWI5d6bd.js} +1 -1
  30. package/dist/gallery/assets/{razor-kebzKtsv.js → razor-CPcSAg2x.js} +1 -1
  31. package/dist/gallery/assets/{tsMode-BZSsu7di.js → tsMode-1ZmI8w72.js} +1 -1
  32. package/dist/gallery/assets/{typescript-MSiFowAO.js → typescript-CVZCJg8D.js} +1 -1
  33. package/dist/gallery/assets/{xml-D6T21GmG.js → xml-B_rQCZJa.js} +1 -1
  34. package/dist/gallery/assets/{yaml-CVRjrT5r.js → yaml-gB0iHXGe.js} +1 -1
  35. package/dist/gallery/index.html +17 -14
  36. package/dist/index-BWuuTDDw.d.mts +151 -0
  37. package/dist/index-BWuuTDDw.d.mts.map +1 -0
  38. package/dist/{index.d.ts → index.d.mts} +6 -224
  39. package/dist/index.d.mts.map +1 -0
  40. package/dist/{index.js → index.mjs} +168 -178
  41. package/dist/index.mjs.map +1 -0
  42. package/dist/{vrt-D6OumJUH.d.ts → vrt-B4uxOrnN.d.mts} +6 -18
  43. package/dist/vrt-B4uxOrnN.d.mts.map +1 -0
  44. package/dist/{vrt-5_c9P1YY.js → vrt-CjFf5GR0.mjs} +39 -47
  45. package/dist/vrt-CjFf5GR0.mjs.map +1 -0
  46. package/dist/vrt.d.mts +2 -0
  47. package/dist/vrt.mjs +2 -0
  48. package/package.json +49 -49
  49. package/dist/a11y-7maCHrYD.js.map +0 -1
  50. package/dist/a11y-CjpWs0s0.js +0 -3
  51. package/dist/autogen-Dx-SIBf_.js +0 -3
  52. package/dist/autogen-dfLosbY_.js.map +0 -1
  53. package/dist/cli/index.d.ts.map +0 -1
  54. package/dist/cli/index.js.map +0 -1
  55. package/dist/gallery/assets/index-Cp7AWs0x.css +0 -1
  56. package/dist/index.css +0 -496
  57. package/dist/index.css.map +0 -1
  58. package/dist/index.d.ts.map +0 -1
  59. package/dist/index.js.map +0 -1
  60. package/dist/vrt-5_c9P1YY.js.map +0 -1
  61. package/dist/vrt-D6OumJUH.d.ts.map +0 -1
  62. package/dist/vrt.d.ts +0 -2
  63. package/dist/vrt.js +0 -3
@@ -1,12 +1,17 @@
1
- import { MuseaVrtRunner, generateVrtJsonReport, generateVrtReport } from "./vrt-5_c9P1YY.js";
2
- import { MuseaA11yRunner } from "./a11y-7maCHrYD.js";
3
- import { generateArtFile, writeArtFile } from "./autogen-dfLosbY_.js";
1
+ import { i as MuseaVrtRunner, n as generateVrtJsonReport, r as generateVrtReport } from "./vrt-CjFf5GR0.mjs";
2
+ import { t as MuseaA11yRunner } from "./a11y-DNCg2qCB.mjs";
3
+ import { n as writeArtFile, t as generateArtFile } from "./autogen-3-y1d0ou.mjs";
4
+ import { createRequire } from "node:module";
4
5
  import fs from "node:fs";
5
6
  import path from "node:path";
6
7
  import { vizeConfigStore } from "@vizejs/vite-plugin";
7
- import { createRequire } from "node:module";
8
-
9
8
  //#region src/native-loader.ts
9
+ /**
10
+ * Native binding loader for @vizejs/native.
11
+ *
12
+ * Provides lazy-loading of the native Rust-based parser and a JS fallback
13
+ * for SFC analysis when the native `analyzeSfc` function is unavailable.
14
+ */
10
15
  let native = null;
11
16
  function loadNative() {
12
17
  if (native) return native;
@@ -28,8 +33,7 @@ function analyzeSfcFallback(source, _options) {
28
33
  const emits = [];
29
34
  const scriptSetupMatch = source.match(/<script\s+[^>]*setup[^>]*>([\s\S]*?)<\/script>/);
30
35
  if (!scriptSetupMatch) {
31
- const scriptMatch = source.match(/<script[^>]*>([\s\S]*?)<\/script>/);
32
- if (!scriptMatch) return {
36
+ if (!source.match(/<script[^>]*>([\s\S]*?)<\/script>/)) return {
33
37
  props: [],
34
38
  emits: []
35
39
  };
@@ -83,9 +87,11 @@ function analyzeSfcFallback(source, _options) {
83
87
  };
84
88
  }
85
89
  }
86
-
87
90
  //#endregion
88
91
  //#region src/utils.ts
92
+ /**
93
+ * Shared utility functions for the Musea Vite plugin.
94
+ */
89
95
  function shouldProcess(file, include, exclude, root) {
90
96
  const relative = path.relative(root, file);
91
97
  for (const pattern of exclude) if (matchGlob(relative, pattern)) return false;
@@ -117,8 +123,7 @@ async function scanArtFiles(root, include, exclude, scanInlineArt = false) {
117
123
  break;
118
124
  }
119
125
  } else if (scanInlineArt && entry.isFile() && entry.name.endsWith(".vue") && !entry.name.endsWith(".art.vue")) {
120
- const content = await fs.promises.readFile(fullPath, "utf-8");
121
- if (content.includes("<art")) files.push(fullPath);
126
+ if ((await fs.promises.readFile(fullPath, "utf-8")).includes("<art")) files.push(fullPath);
122
127
  }
123
128
  }
124
129
  }
@@ -165,15 +170,19 @@ function buildThemeConfig(theme) {
165
170
  custom
166
171
  };
167
172
  }
168
-
169
173
  //#endregion
170
174
  //#region src/art-module.ts
171
175
  /**
176
+ * Art module generation for Musea.
177
+ *
178
+ * Generates the virtual ES modules that represent parsed `.art.vue` files,
179
+ * including variant component definitions and script setup handling.
180
+ */
181
+ /**
172
182
  * Extract the content of the first <script setup> block from a Vue SFC source.
173
183
  */
174
184
  function extractScriptSetupContent(source) {
175
- const match = source.match(/<script\s+[^>]*setup[^>]*>([\s\S]*?)<\/script>/);
176
- return match?.[1]?.trim();
185
+ return source.match(/<script\s+[^>]*setup[^>]*>([\s\S]*?)<\/script>/)?.[1]?.trim();
177
186
  }
178
187
  /**
179
188
  * Parse script setup content into imports and setup body.
@@ -183,7 +192,7 @@ function parseScriptSetupForArt(content) {
183
192
  const lines = content.split("\n");
184
193
  const imports = [];
185
194
  const setupBody = [];
186
- const returnNames = new Set();
195
+ const returnNames = /* @__PURE__ */ new Set();
187
196
  for (const line of lines) {
188
197
  const trimmed = line.trim();
189
198
  if (!trimmed || trimmed.startsWith("//")) continue;
@@ -239,18 +248,16 @@ import { defineComponent, h } from 'vue';
239
248
  const artDir = path.dirname(filePath);
240
249
  for (const imp of scriptSetup.imports) {
241
250
  const resolved = imp.replace(/from\s+(['"])(\.[^'"]+)\1/, (_match, quote, relPath) => {
242
- const absPath = path.resolve(artDir, relPath);
243
- return `from ${quote}${absPath}${quote}`;
251
+ return `from ${quote}${path.resolve(artDir, relPath)}${quote}`;
244
252
  });
245
253
  code += `${resolved}\n`;
246
254
  }
247
255
  }
248
256
  if (componentImportPath && componentName) {
249
- const alreadyImported = scriptSetup?.imports.some((imp) => {
257
+ if (!scriptSetup?.imports.some((imp) => {
250
258
  if (imp.includes(`from '${componentImportPath}'`) || imp.includes(`from "${componentImportPath}"`)) return true;
251
259
  return new RegExp(`^import\\s+${componentName}[\\s,]`).test(imp.trim());
252
- });
253
- if (!alreadyImported) code += `import ${componentName} from '${componentImportPath}';\n`;
260
+ })) code += `import ${componentName} from '${componentImportPath}';\n`;
254
261
  code += `export const __component__ = ${componentName};\n`;
255
262
  }
256
263
  code += `
@@ -263,7 +270,7 @@ export const variants = ${JSON.stringify(art.variants)};
263
270
  if (componentName) template = template.replace(/<Self/g, `<${componentName}`).replace(/<\/Self>/g, `</${componentName}>`);
264
271
  const escapedTemplate = template.replace(/\\/g, "\\\\").replace(/`/g, "\\`").replace(/\$/g, "\\$");
265
272
  const fullTemplate = `<div data-variant="${variant.name}">${escapedTemplate}</div>`;
266
- const componentNames = new Set();
273
+ const componentNames = /* @__PURE__ */ new Set();
267
274
  if (componentName) componentNames.add(componentName);
268
275
  if (scriptSetup) {
269
276
  for (const name of scriptSetup.returnNames) if (/^[A-Z]/.test(name)) componentNames.add(name);
@@ -298,28 +305,29 @@ export default ${toPascalCase(defaultVariant.name)};
298
305
  `;
299
306
  return code;
300
307
  }
301
-
302
308
  //#endregion
303
- //#region src/gallery/styles-base.css
304
- var styles_base_default = {};
305
-
309
+ //#region src/gallery/styles-base.css?inline
310
+ var styles_base_default = ":root {\n --musea-bg-primary: #e6e2d6;\n --musea-bg-secondary: #ddd9cd;\n --musea-bg-tertiary: #d4d0c4;\n --musea-bg-elevated: #e6e2d6;\n --musea-accent: #121212;\n --musea-accent-hover: #2a2a2a;\n --musea-accent-subtle: #12121214;\n --musea-text: #121212;\n --musea-text-secondary: #3a3a3a;\n --musea-text-muted: #6b6b6b;\n --musea-border: #c8c4b8;\n --musea-border-subtle: #d4d0c4;\n --musea-success: #16a34a;\n --musea-shadow: 0 4px 24px #00000014;\n --musea-radius-sm: 4px;\n --musea-radius-md: 6px;\n --musea-radius-lg: 8px;\n --musea-transition: .15s ease;\n}\n\n* {\n box-sizing: border-box;\n margin: 0;\n padding: 0;\n}\n\nbody {\n background: var(--musea-bg-primary);\n color: var(--musea-text);\n -webkit-font-smoothing: antialiased;\n min-height: 100vh;\n font-family: Helvetica Neue, Helvetica, Arial, sans-serif;\n line-height: 1.5;\n}\n";
306
311
  //#endregion
307
- //#region src/gallery/styles-layout.css
308
- var styles_layout_default = {};
309
-
312
+ //#region src/gallery/styles-layout.css?inline
313
+ var styles_layout_default = ".header {\n background: var(--musea-bg-secondary);\n border-bottom: 1px solid var(--musea-border);\n z-index: 100;\n justify-content: space-between;\n align-items: center;\n height: 56px;\n padding: 0 1.5rem;\n display: flex;\n position: sticky;\n top: 0;\n}\n\n.header-left {\n align-items: center;\n gap: 1.5rem;\n display: flex;\n}\n\n.logo {\n color: var(--musea-accent);\n align-items: center;\n gap: .5rem;\n font-size: 1.125rem;\n font-weight: 700;\n text-decoration: none;\n display: flex;\n}\n\n.logo-svg {\n flex-shrink: 0;\n width: 32px;\n height: 32px;\n}\n\n.logo-icon svg {\n width: 16px;\n height: 16px;\n color: var(--musea-text);\n}\n\n.header-subtitle {\n color: var(--musea-text-muted);\n border-left: 1px solid var(--musea-border);\n padding-left: 1.5rem;\n font-size: .8125rem;\n font-weight: 500;\n}\n\n.search-container {\n width: 280px;\n position: relative;\n}\n\n.search-input {\n background: var(--musea-bg-tertiary);\n border: 1px solid var(--musea-border);\n border-radius: var(--musea-radius-md);\n width: 100%;\n color: var(--musea-text);\n transition: border-color var(--musea-transition),\n background var(--musea-transition);\n outline: none;\n padding: .5rem .75rem .5rem 2.25rem;\n font-size: .8125rem;\n}\n\n.search-input::placeholder {\n color: var(--musea-text-muted);\n}\n\n.search-input:focus {\n border-color: var(--musea-accent);\n background: var(--musea-bg-elevated);\n}\n\n.search-icon {\n color: var(--musea-text-muted);\n pointer-events: none;\n position: absolute;\n top: 50%;\n left: .75rem;\n transform: translateY(-50%);\n}\n\n.main {\n grid-template-columns: 260px 1fr;\n min-height: calc(100vh - 56px);\n display: grid;\n}\n\n.sidebar {\n background: var(--musea-bg-secondary);\n border-right: 1px solid var(--musea-border);\n overflow: hidden auto;\n}\n\n.sidebar::-webkit-scrollbar {\n width: 6px;\n}\n\n.sidebar::-webkit-scrollbar-track {\n background: none;\n}\n\n.sidebar::-webkit-scrollbar-thumb {\n background: var(--musea-border);\n border-radius: 3px;\n}\n\n.sidebar-section {\n padding: .75rem;\n}\n\n.category-header {\n text-transform: uppercase;\n letter-spacing: .08em;\n color: var(--musea-text-muted);\n cursor: pointer;\n user-select: none;\n border-radius: var(--musea-radius-sm);\n transition: background var(--musea-transition);\n align-items: center;\n gap: .5rem;\n padding: .625rem .75rem;\n font-size: .6875rem;\n font-weight: 600;\n display: flex;\n}\n\n.category-header:hover {\n background: var(--musea-bg-tertiary);\n}\n\n.category-icon {\n width: 16px;\n height: 16px;\n transition: transform var(--musea-transition);\n}\n\n.category-header.collapsed .category-icon {\n transform: rotate(-90deg);\n}\n\n.category-count {\n background: var(--musea-bg-tertiary);\n border-radius: 4px;\n margin-left: auto;\n padding: .125rem .375rem;\n font-size: .625rem;\n}\n\n.art-list {\n margin-top: .25rem;\n list-style: none;\n}\n\n.art-item {\n border-radius: var(--musea-radius-sm);\n cursor: pointer;\n color: var(--musea-text-secondary);\n transition: all var(--musea-transition);\n align-items: center;\n gap: .625rem;\n padding: .5rem .75rem .5rem 1.75rem;\n font-size: .8125rem;\n display: flex;\n position: relative;\n}\n\n.art-item:before {\n content: \"\";\n background: var(--musea-border);\n width: 6px;\n height: 6px;\n transition: background var(--musea-transition);\n border-radius: 50%;\n position: absolute;\n top: 50%;\n left: .75rem;\n transform: translateY(-50%);\n}\n\n.art-item:hover {\n background: var(--musea-bg-tertiary);\n color: var(--musea-text);\n}\n\n.art-item:hover:before {\n background: var(--musea-text-muted);\n}\n\n.art-item.active {\n background: var(--musea-accent-subtle);\n color: var(--musea-accent-hover);\n}\n\n.art-item.active:before {\n background: var(--musea-accent);\n}\n\n.art-variant-count {\n color: var(--musea-text-muted);\n opacity: 0;\n transition: opacity var(--musea-transition);\n margin-left: auto;\n font-size: .6875rem;\n}\n\n.art-item:hover .art-variant-count {\n opacity: 1;\n}\n\n.content {\n background: var(--musea-bg-primary);\n overflow-y: auto;\n}\n\n.content-inner {\n max-width: 1400px;\n margin: 0 auto;\n padding: 2rem;\n}\n\n.content-header {\n margin-bottom: 2rem;\n}\n\n.content-title {\n margin-bottom: .5rem;\n font-size: 1.5rem;\n font-weight: 700;\n}\n\n.content-description {\n color: var(--musea-text-muted);\n max-width: 600px;\n font-size: .9375rem;\n}\n\n.content-meta {\n align-items: center;\n gap: 1rem;\n margin-top: 1rem;\n display: flex;\n}\n\n.meta-tag {\n background: var(--musea-bg-secondary);\n border: 1px solid var(--musea-border);\n border-radius: var(--musea-radius-sm);\n color: var(--musea-text-muted);\n align-items: center;\n gap: .375rem;\n padding: .25rem .625rem;\n font-size: .75rem;\n display: inline-flex;\n}\n\n.meta-tag svg {\n width: 12px;\n height: 12px;\n}\n";
310
314
  //#endregion
311
- //#region src/gallery/styles-components.css
312
- var styles_components_default = {};
313
-
315
+ //#region src/gallery/styles-components.css?inline
316
+ var styles_components_default = ".gallery {\n grid-template-columns: repeat(auto-fill, minmax(320px, 1fr));\n gap: 1.25rem;\n display: grid;\n}\n\n.variant-card {\n background: var(--musea-bg-secondary);\n border: 1px solid var(--musea-border);\n border-radius: var(--musea-radius-lg);\n transition: all var(--musea-transition);\n overflow: hidden;\n}\n\n.variant-card:hover {\n border-color: var(--musea-text-muted);\n box-shadow: var(--musea-shadow);\n transform: translateY(-2px);\n}\n\n.variant-preview {\n aspect-ratio: 16 / 10;\n background: var(--musea-bg-tertiary);\n justify-content: center;\n align-items: center;\n display: flex;\n position: relative;\n overflow: hidden;\n}\n\n.variant-preview iframe {\n background: #fff;\n border: none;\n width: 100%;\n height: 100%;\n}\n\n.variant-preview-placeholder {\n color: var(--musea-text-muted);\n text-align: center;\n padding: 1rem;\n font-size: .8125rem;\n}\n\n.variant-preview-code {\n color: var(--musea-text-muted);\n background: var(--musea-bg-primary);\n width: 100%;\n max-height: 100%;\n padding: 1rem;\n font-family: JetBrains Mono, SF Mono, Fira Code, monospace;\n font-size: .75rem;\n overflow: auto;\n}\n\n.variant-info {\n border-top: 1px solid var(--musea-border);\n justify-content: space-between;\n align-items: center;\n padding: 1rem;\n display: flex;\n}\n\n.variant-name {\n font-size: .875rem;\n font-weight: 600;\n}\n\n.variant-badge {\n text-transform: uppercase;\n letter-spacing: .04em;\n background: var(--musea-accent-subtle);\n color: var(--musea-accent);\n border-radius: 4px;\n padding: .1875rem .5rem;\n font-size: .625rem;\n font-weight: 600;\n}\n\n.variant-actions {\n gap: .5rem;\n display: flex;\n}\n\n.variant-action-btn {\n background: var(--musea-bg-tertiary);\n border-radius: var(--musea-radius-sm);\n width: 28px;\n height: 28px;\n color: var(--musea-text-muted);\n cursor: pointer;\n transition: all var(--musea-transition);\n border: none;\n justify-content: center;\n align-items: center;\n display: flex;\n}\n\n.variant-action-btn:hover {\n background: var(--musea-bg-elevated);\n color: var(--musea-text);\n}\n\n.variant-action-btn svg {\n width: 14px;\n height: 14px;\n}\n\n.empty-state {\n text-align: center;\n flex-direction: column;\n justify-content: center;\n align-items: center;\n min-height: 400px;\n padding: 2rem;\n display: flex;\n}\n\n.empty-state-icon {\n background: var(--musea-bg-secondary);\n border-radius: var(--musea-radius-lg);\n justify-content: center;\n align-items: center;\n width: 80px;\n height: 80px;\n margin-bottom: 1.5rem;\n display: flex;\n}\n\n.empty-state-icon svg {\n width: 40px;\n height: 40px;\n color: var(--musea-text-muted);\n}\n\n.empty-state-title {\n margin-bottom: .5rem;\n font-size: 1.125rem;\n font-weight: 600;\n}\n\n.empty-state-text {\n color: var(--musea-text-muted);\n max-width: 300px;\n font-size: .875rem;\n}\n\n.loading {\n min-height: 200px;\n color: var(--musea-text-muted);\n justify-content: center;\n align-items: center;\n gap: .75rem;\n display: flex;\n}\n\n.loading-spinner {\n border: 2px solid var(--musea-border);\n border-top-color: var(--musea-accent);\n border-radius: 50%;\n width: 20px;\n height: 20px;\n animation: .8s linear infinite spin;\n}\n\n@keyframes spin {\n to {\n transform: rotate(360deg);\n }\n}\n\n@media (width <= 768px) {\n .main {\n grid-template-columns: 1fr;\n }\n\n .sidebar, .header-subtitle {\n display: none;\n }\n}\n";
314
317
  //#endregion
315
318
  //#region src/gallery/styles.ts
316
319
  /**
320
+ * CSS theme variables and style definitions for the Musea gallery.
321
+ *
322
+ * CSS is split into separate .css files and imported as text
323
+ * via tsdown's `?inline` support.
324
+ */
325
+ /**
317
326
  * Generate the full gallery CSS styles string.
318
327
  */
319
328
  function generateGalleryStyles() {
320
329
  return `${styles_base_default}\n${styles_layout_default}\n${styles_components_default}`;
321
330
  }
322
-
323
331
  //#endregion
324
332
  //#region src/gallery/template.ts
325
333
  /**
@@ -552,28 +560,32 @@ function generateGalleryScript(basePath) {
552
560
 
553
561
  loadArts();`;
554
562
  }
555
-
556
563
  //#endregion
557
564
  //#region src/gallery/index.ts
558
565
  /**
566
+ * Gallery HTML generation for the Musea component gallery.
567
+ *
568
+ * Contains the inline gallery SPA template (used as a fallback when the
569
+ * pre-built gallery is not available) and the gallery virtual module.
570
+ */
571
+ /**
559
572
  * Generate the inline gallery HTML page.
560
573
  */
561
574
  function generateGalleryHtml(basePath, themeConfig) {
562
- const themeScript = themeConfig ? `window.__MUSEA_THEME_CONFIG__=${JSON.stringify(themeConfig)};` : "";
563
575
  return `<!DOCTYPE html>
564
576
  <html lang="en">
565
577
  <head>
566
578
  <meta charset="UTF-8">
567
579
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
568
580
  <title>Musea - Component Gallery</title>
569
- <script>window.__MUSEA_BASE_PATH__='${basePath}';${themeScript}</script>
581
+ <script>window.__MUSEA_BASE_PATH__='${basePath}';${themeConfig ? `window.__MUSEA_THEME_CONFIG__=${JSON.stringify(themeConfig)};` : ""}<\/script>
570
582
  <style>${generateGalleryStyles()}
571
583
  </style>
572
584
  </head>
573
585
  <body>${generateGalleryBody(basePath)}
574
586
 
575
587
  <script type="module">${generateGalleryScript(basePath)}
576
- </script>
588
+ <\/script>
577
589
  </body>
578
590
  </html>`;
579
591
  }
@@ -589,7 +601,6 @@ export async function loadArts() {
589
601
  }
590
602
  `;
591
603
  }
592
-
593
604
  //#endregion
594
605
  //#region src/preview/addons.ts
595
606
  /**
@@ -892,7 +903,6 @@ function __museaInitAddons(container, variantName) {
892
903
  window.parent.postMessage({ type: 'musea:ready', payload: {} }, '*');
893
904
  }
894
905
  `;
895
-
896
906
  //#endregion
897
907
  //#region src/preview/html.ts
898
908
  function generatePreviewHtml(art, variant, _basePath, viteBase) {
@@ -904,7 +914,7 @@ function generatePreviewHtml(art, variant, _basePath, viteBase) {
904
914
  <meta charset="UTF-8">
905
915
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
906
916
  <title>${escapeHtml(art.metadata.title)} - ${escapeHtml(variant.name)}</title>
907
- <script type="module" src="${base}/@vite/client"></script>
917
+ <script type="module" src="${base}/@vite/client"><\/script>
908
918
  <style>
909
919
  * { box-sizing: border-box; margin: 0; padding: 0; }
910
920
  html, body {
@@ -989,11 +999,10 @@ function generatePreviewHtml(art, variant, _basePath, viteBase) {
989
999
  Loading component...
990
1000
  </div>
991
1001
  </div>
992
- <script type="module" src="${previewModuleUrl}"></script>
1002
+ <script type="module" src="${previewModuleUrl}"><\/script>
993
1003
  </body>
994
1004
  </html>`;
995
1005
  }
996
-
997
1006
  //#endregion
998
1007
  //#region src/preview/index.ts
999
1008
  function generatePreviewModule(art, variantComponentName, variantName, cssImports = [], previewSetup = null) {
@@ -1108,12 +1117,9 @@ function generatePreviewModuleWithProps(art, variantComponentName, variantName,
1108
1117
  const artModuleId = `virtual:musea-art:${art.path}`;
1109
1118
  const escapedVariantName = escapeTemplate(variantName);
1110
1119
  const propsJson = JSON.stringify(propsOverride);
1111
- const cssImportStatements = cssImports.map((cssPath) => `import '${cssPath}';`).join("\n");
1112
- const setupImport = previewSetup ? `import __museaPreviewSetup from '${previewSetup}';` : "";
1113
- const setupCall = previewSetup ? "await __museaPreviewSetup(app);" : "";
1114
1120
  return `
1115
- ${cssImportStatements}
1116
- ${setupImport}
1121
+ ${cssImports.map((cssPath) => `import '${cssPath}';`).join("\n")}
1122
+ ${previewSetup ? `import __museaPreviewSetup from '${previewSetup}';` : ""}
1117
1123
  import { createApp, h } from 'vue';
1118
1124
  import * as artModule from '${artModuleId}';
1119
1125
 
@@ -1136,7 +1142,7 @@ async function mount() {
1136
1142
  };
1137
1143
 
1138
1144
  const app = createApp(WrappedComponent);
1139
- ${setupCall}
1145
+ ${previewSetup ? "await __museaPreviewSetup(app);" : ""}
1140
1146
  container.innerHTML = '';
1141
1147
  container.className = 'musea-variant';
1142
1148
  app.mount(container);
@@ -1151,7 +1157,6 @@ async function mount() {
1151
1157
  mount();
1152
1158
  `;
1153
1159
  }
1154
-
1155
1160
  //#endregion
1156
1161
  //#region src/server-middleware.ts
1157
1162
  /**
@@ -1176,7 +1181,7 @@ function registerMiddleware(devServer, ctx) {
1176
1181
  await fs.promises.access(indexHtmlPath);
1177
1182
  let html = await fs.promises.readFile(indexHtmlPath, "utf-8");
1178
1183
  const themeScript = themeConfig ? `window.__MUSEA_THEME_CONFIG__=${JSON.stringify(themeConfig)};` : "";
1179
- html = html.replace("</head>", `<script>window.__MUSEA_BASE_PATH__='${basePath}';${themeScript}</script></head>`);
1184
+ html = html.replace("</head>", `<script>window.__MUSEA_BASE_PATH__='${basePath}';${themeScript}<\/script></head>`);
1180
1185
  res.setHeader("Content-Type", "text/html");
1181
1186
  res.end(html);
1182
1187
  return;
@@ -1191,11 +1196,10 @@ function registerMiddleware(devServer, ctx) {
1191
1196
  const galleryDistDir = path.resolve(path.dirname(new URL(import.meta.url).pathname), "gallery");
1192
1197
  const filePath = path.join(galleryDistDir, url);
1193
1198
  try {
1194
- const stat = await fs.promises.stat(filePath);
1195
- if (stat.isFile()) {
1199
+ if ((await fs.promises.stat(filePath)).isFile()) {
1196
1200
  const content = await fs.promises.readFile(filePath);
1197
1201
  const ext = path.extname(filePath);
1198
- const mimeTypes = {
1202
+ res.setHeader("Content-Type", {
1199
1203
  ".js": "application/javascript",
1200
1204
  ".css": "text/css",
1201
1205
  ".svg": "image/svg+xml",
@@ -1203,8 +1207,7 @@ function registerMiddleware(devServer, ctx) {
1203
1207
  ".ico": "image/x-icon",
1204
1208
  ".woff2": "font/woff2",
1205
1209
  ".woff": "font/woff"
1206
- };
1207
- res.setHeader("Content-Type", mimeTypes[ext] || "application/octet-stream");
1210
+ }[ext] || "application/octet-stream");
1208
1211
  res.setHeader("Cache-Control", "public, max-age=31536000, immutable");
1209
1212
  res.end(content);
1210
1213
  return;
@@ -1215,8 +1218,7 @@ function registerMiddleware(devServer, ctx) {
1215
1218
  });
1216
1219
  devServer.middlewares.use(`${basePath}/vendor/axe-core.min.js`, async (_req, res, _next) => {
1217
1220
  try {
1218
- const require = createRequire(import.meta.url);
1219
- const axeCorePath = require.resolve("axe-core/axe.min.js");
1221
+ const axeCorePath = createRequire(import.meta.url).resolve("axe-core/axe.min.js");
1220
1222
  const content = await fs.promises.readFile(axeCorePath, "utf-8");
1221
1223
  res.setHeader("Content-Type", "application/javascript");
1222
1224
  res.setHeader("Cache-Control", "public, max-age=86400");
@@ -1247,8 +1249,7 @@ function registerMiddleware(devServer, ctx) {
1247
1249
  res.end("Variant not found");
1248
1250
  return;
1249
1251
  }
1250
- const variantComponentName = toPascalCase(variant.name);
1251
- const moduleCode = generatePreviewModule(art, variantComponentName, variant.name, ctx.resolvedPreviewCss, ctx.resolvedPreviewSetup);
1252
+ const moduleCode = generatePreviewModule(art, toPascalCase(variant.name), variant.name, ctx.resolvedPreviewCss, ctx.resolvedPreviewSetup);
1252
1253
  try {
1253
1254
  const result = await devServer.transformRequest(`virtual:musea-preview:${artPath}:${variantName}`);
1254
1255
  if (result) {
@@ -1321,19 +1322,22 @@ function registerMiddleware(devServer, ctx) {
1321
1322
  }
1322
1323
  });
1323
1324
  }
1324
-
1325
1325
  //#endregion
1326
1326
  //#region src/tokens/parser.ts
1327
1327
  /**
1328
+ * Token parsing utilities for Style Dictionary integration.
1329
+ *
1330
+ * Reads and parses design token files (JSON) and directories,
1331
+ * flattening nested structures into categorized token collections.
1332
+ */
1333
+ /**
1328
1334
  * Parse Style Dictionary tokens file.
1329
1335
  */
1330
1336
  async function parseTokens(tokensPath) {
1331
1337
  const absolutePath = path.resolve(tokensPath);
1332
- const stat = await fs.promises.stat(absolutePath);
1333
- if (stat.isDirectory()) return parseTokenDirectory(absolutePath);
1338
+ if ((await fs.promises.stat(absolutePath)).isDirectory()) return parseTokenDirectory(absolutePath);
1334
1339
  const content = await fs.promises.readFile(absolutePath, "utf-8");
1335
- const tokens = JSON.parse(content);
1336
- return flattenTokens(tokens);
1340
+ return flattenTokens(JSON.parse(content));
1337
1341
  }
1338
1342
  /**
1339
1343
  * Parse tokens from a directory.
@@ -1425,10 +1429,15 @@ function normalizeToken(raw) {
1425
1429
  function formatCategoryName(name) {
1426
1430
  return name.replace(/[-_]/g, " ").replace(/([a-z])([A-Z])/g, "$1 $2").split(" ").map((word) => word.charAt(0).toUpperCase() + word.slice(1).toLowerCase()).join(" ");
1427
1431
  }
1428
-
1429
1432
  //#endregion
1430
1433
  //#region src/tokens/usage.ts
1431
1434
  /**
1435
+ * Token usage scanning and value normalization.
1436
+ *
1437
+ * Scans art file `<style>` blocks for CSS property values that match
1438
+ * design token values, and provides value normalization utilities.
1439
+ */
1440
+ /**
1432
1441
  * Normalize a token value for comparison.
1433
1442
  * - Lowercase, trim
1434
1443
  * - Leading-zero: `.5rem` -> `0.5rem`
@@ -1450,10 +1459,9 @@ const CSS_PROPERTY_RE = /^\s*([\w-]+)\s*:\s*(.+?)\s*;?\s*$/;
1450
1459
  * Scan art file sources for token value matches in `<style>` blocks.
1451
1460
  */
1452
1461
  function scanTokenUsage(artFiles, tokenMap) {
1453
- const valueLookup = new Map();
1462
+ const valueLookup = /* @__PURE__ */ new Map();
1454
1463
  for (const [tokenPath, token] of Object.entries(tokenMap)) {
1455
- const rawValue = token.$resolvedValue ?? token.value;
1456
- const normalized = normalizeTokenValue(rawValue);
1464
+ const normalized = normalizeTokenValue(token.$resolvedValue ?? token.value);
1457
1465
  if (!normalized) continue;
1458
1466
  const existing = valueLookup.get(normalized);
1459
1467
  if (existing) existing.push(tokenPath);
@@ -1487,8 +1495,7 @@ function scanTokenUsage(artFiles, tokenMap) {
1487
1495
  const propMatch = line.match(CSS_PROPERTY_RE);
1488
1496
  if (!propMatch) continue;
1489
1497
  const property = propMatch[1];
1490
- const valueStr = propMatch[2];
1491
- const valueParts = valueStr.split(/\s+/);
1498
+ const valueParts = propMatch[2].split(/\s+/);
1492
1499
  for (const part of valueParts) {
1493
1500
  const normalizedPart = normalizeTokenValue(part);
1494
1501
  const matchingTokens = valueLookup.get(normalizedPart);
@@ -1519,9 +1526,14 @@ function scanTokenUsage(artFiles, tokenMap) {
1519
1526
  }
1520
1527
  return usageMap;
1521
1528
  }
1522
-
1523
1529
  //#endregion
1524
1530
  //#region src/tokens/resolver.ts
1531
+ /**
1532
+ * Token resolution, CRUD operations, and validation.
1533
+ *
1534
+ * Handles building flat token maps from categories, resolving reference chains,
1535
+ * reading/writing raw token files, and validating semantic references.
1536
+ */
1525
1537
  const REFERENCE_PATTERN = /^\{(.+)\}$/;
1526
1538
  const MAX_RESOLVE_DEPTH = 10;
1527
1539
  /**
@@ -1558,7 +1570,7 @@ function resolveTokenReference(token, tokenMap) {
1558
1570
  if (match) {
1559
1571
  token.$tier = token.$tier ?? "semantic";
1560
1572
  token.$reference = match[1];
1561
- token.$resolvedValue = resolveValue(match[1], tokenMap, 0, new Set());
1573
+ token.$resolvedValue = resolveValue(match[1], tokenMap, 0, /* @__PURE__ */ new Set());
1562
1574
  return;
1563
1575
  }
1564
1576
  }
@@ -1645,7 +1657,7 @@ function validateSemanticReference(tokenMap, reference, selfPath) {
1645
1657
  valid: false,
1646
1658
  error: `Reference target "${reference}" does not exist`
1647
1659
  };
1648
- const visited = new Set();
1660
+ const visited = /* @__PURE__ */ new Set();
1649
1661
  if (selfPath) visited.add(selfPath);
1650
1662
  let current = reference;
1651
1663
  let depth = 0;
@@ -1678,25 +1690,29 @@ function validateSemanticReference(tokenMap, reference, selfPath) {
1678
1690
  */
1679
1691
  function findDependentTokens(tokenMap, targetPath) {
1680
1692
  const dependents = [];
1681
- for (const [path$1, token] of Object.entries(tokenMap)) if (typeof token.value === "string") {
1693
+ for (const [path, token] of Object.entries(tokenMap)) if (typeof token.value === "string") {
1682
1694
  const match = token.value.match(REFERENCE_PATTERN);
1683
- if (match && match[1] === targetPath) dependents.push(path$1);
1695
+ if (match && match[1] === targetPath) dependents.push(path);
1684
1696
  }
1685
1697
  return dependents;
1686
1698
  }
1687
-
1688
1699
  //#endregion
1689
1700
  //#region src/tokens/generator.ts
1690
1701
  /**
1702
+ * Token documentation generators for Style Dictionary integration.
1703
+ *
1704
+ * Generates HTML, Markdown, and JSON documentation from parsed token categories,
1705
+ * and provides the main processStyleDictionary orchestrator function.
1706
+ */
1707
+ /**
1691
1708
  * Generate HTML documentation for tokens.
1692
1709
  */
1693
1710
  function generateTokensHtml(categories) {
1694
1711
  const renderToken = (name, token) => {
1695
- const isColor = typeof token.value === "string" && (token.value.startsWith("#") || token.value.startsWith("rgb") || token.value.startsWith("hsl") || token.type === "color");
1696
1712
  return `
1697
1713
  <div class="token">
1698
1714
  <div class="token-preview">
1699
- ${isColor ? `<div class="color-swatch" style="background: ${token.value}"></div>` : ""}
1715
+ ${typeof token.value === "string" && (token.value.startsWith("#") || token.value.startsWith("rgb") || token.value.startsWith("hsl") || token.type === "color") ? `<div class="color-swatch" style="background: ${token.value}"></div>` : ""}
1700
1716
  </div>
1701
1717
  <div class="token-info">
1702
1718
  <div class="token-name">${name}</div>
@@ -1803,8 +1819,7 @@ function generateTokensHtml(categories) {
1803
1819
  */
1804
1820
  function generateTokensMarkdown(categories) {
1805
1821
  const renderCategory = (category, level = 2) => {
1806
- const heading = "#".repeat(level);
1807
- let md = `\n${heading} ${category.name}\n\n`;
1822
+ let md = `\n${"#".repeat(level)} ${category.name}\n\n`;
1808
1823
  if (Object.keys(category.tokens).length > 0) {
1809
1824
  md += "| Token | Value | Description |\n";
1810
1825
  md += "|-------|-------|-------------|\n";
@@ -1818,7 +1833,7 @@ function generateTokensMarkdown(categories) {
1818
1833
  return md;
1819
1834
  };
1820
1835
  let markdown = "# Design Tokens\n\n";
1821
- markdown += `> Generated by Musea on ${new Date().toISOString()}\n`;
1836
+ markdown += `> Generated by Musea on ${(/* @__PURE__ */ new Date()).toISOString()}\n`;
1822
1837
  for (const category of categories) markdown += renderCategory(category);
1823
1838
  return markdown;
1824
1839
  }
@@ -1842,7 +1857,6 @@ async function processStyleDictionary(config) {
1842
1857
  content = generateTokensMarkdown(categories);
1843
1858
  filename = "tokens.md";
1844
1859
  break;
1845
- case "json":
1846
1860
  default:
1847
1861
  content = JSON.stringify({ categories }, null, 2);
1848
1862
  filename = "tokens.json";
@@ -1854,13 +1868,22 @@ async function processStyleDictionary(config) {
1854
1868
  categories,
1855
1869
  metadata: {
1856
1870
  name: path.basename(config.tokensPath),
1857
- generatedAt: new Date().toISOString()
1871
+ generatedAt: (/* @__PURE__ */ new Date()).toISOString()
1858
1872
  }
1859
1873
  };
1860
1874
  }
1861
-
1862
1875
  //#endregion
1863
1876
  //#region src/api-tokens.ts
1877
+ /**
1878
+ * Musea gallery API token route handlers.
1879
+ *
1880
+ * Handles GET/POST/PUT/DELETE for /api/tokens endpoints:
1881
+ * - GET /tokens -- list all resolved design tokens
1882
+ * - GET /tokens/usage -- token usage across art files
1883
+ * - POST /tokens -- create a new token
1884
+ * - PUT /tokens -- update an existing token
1885
+ * - DELETE /tokens -- delete a token
1886
+ */
1864
1887
  /** GET /api/tokens/usage */
1865
1888
  async function handleTokensUsage(ctx, sendJson) {
1866
1889
  if (!ctx.tokensPath) {
@@ -1868,13 +1891,10 @@ async function handleTokensUsage(ctx, sendJson) {
1868
1891
  return;
1869
1892
  }
1870
1893
  try {
1871
- const absoluteTokensPath = path.resolve(ctx.config.root, ctx.tokensPath);
1872
- const categories = await parseTokens(absoluteTokensPath);
1873
- const tokenMap = buildTokenMap(categories);
1874
- resolveReferences(categories, tokenMap);
1894
+ const categories = await parseTokens(path.resolve(ctx.config.root, ctx.tokensPath));
1895
+ resolveReferences(categories, buildTokenMap(categories));
1875
1896
  const resolvedTokenMap = buildTokenMap(categories);
1876
- const usage = scanTokenUsage(ctx.artFiles, resolvedTokenMap);
1877
- sendJson(usage);
1897
+ sendJson(scanTokenUsage(ctx.artFiles, resolvedTokenMap));
1878
1898
  } catch (e) {
1879
1899
  console.error("[musea] Failed to scan token usage:", e);
1880
1900
  sendJson({});
@@ -1898,8 +1918,7 @@ async function handleTokensGet(ctx, sendJson) {
1898
1918
  try {
1899
1919
  const absoluteTokensPath = path.resolve(ctx.config.root, ctx.tokensPath);
1900
1920
  const categories = await parseTokens(absoluteTokensPath);
1901
- const tokenMap = buildTokenMap(categories);
1902
- resolveReferences(categories, tokenMap);
1921
+ resolveReferences(categories, buildTokenMap(categories));
1903
1922
  const resolvedTokenMap = buildTokenMap(categories);
1904
1923
  let primitiveCount = 0;
1905
1924
  let semanticCount = 0;
@@ -1939,8 +1958,7 @@ async function handleTokensCreate(ctx, readBody, sendJson, sendError) {
1939
1958
  }
1940
1959
  const absoluteTokensPath = path.resolve(ctx.config.root, ctx.tokensPath);
1941
1960
  const rawData = await readRawTokenFile(absoluteTokensPath);
1942
- const currentCategories = await parseTokens(absoluteTokensPath);
1943
- const currentMap = buildTokenMap(currentCategories);
1961
+ const currentMap = buildTokenMap(await parseTokens(absoluteTokensPath));
1944
1962
  if (currentMap[dotPath]) {
1945
1963
  sendError(`Token already exists at path "${dotPath}"`, 409);
1946
1964
  return;
@@ -1957,12 +1975,10 @@ async function handleTokensCreate(ctx, readBody, sendJson, sendError) {
1957
1975
  setTokenAtPath(rawData, dotPath, token);
1958
1976
  await writeRawTokenFile(absoluteTokensPath, rawData);
1959
1977
  const categories = await parseTokens(absoluteTokensPath);
1960
- const tokenMap = buildTokenMap(categories);
1961
- resolveReferences(categories, tokenMap);
1962
- const resolvedTokenMap = buildTokenMap(categories);
1978
+ resolveReferences(categories, buildTokenMap(categories));
1963
1979
  sendJson({
1964
1980
  categories,
1965
- tokenMap: resolvedTokenMap
1981
+ tokenMap: buildTokenMap(categories)
1966
1982
  }, 201);
1967
1983
  } catch (e) {
1968
1984
  sendError(e instanceof Error ? e.message : String(e));
@@ -1983,9 +1999,7 @@ async function handleTokensUpdate(ctx, readBody, sendJson, sendError) {
1983
1999
  }
1984
2000
  const absoluteTokensPath = path.resolve(ctx.config.root, ctx.tokensPath);
1985
2001
  if (token.$reference) {
1986
- const currentCategories = await parseTokens(absoluteTokensPath);
1987
- const currentMap = buildTokenMap(currentCategories);
1988
- const validation = validateSemanticReference(currentMap, token.$reference, dotPath);
2002
+ const validation = validateSemanticReference(buildTokenMap(await parseTokens(absoluteTokensPath)), token.$reference, dotPath);
1989
2003
  if (!validation.valid) {
1990
2004
  sendError(validation.error, 400);
1991
2005
  return;
@@ -1997,12 +2011,10 @@ async function handleTokensUpdate(ctx, readBody, sendJson, sendError) {
1997
2011
  setTokenAtPath(rawData, dotPath, token);
1998
2012
  await writeRawTokenFile(absoluteTokensPath, rawData);
1999
2013
  const categories = await parseTokens(absoluteTokensPath);
2000
- const tokenMap = buildTokenMap(categories);
2001
- resolveReferences(categories, tokenMap);
2002
- const resolvedTokenMap = buildTokenMap(categories);
2014
+ resolveReferences(categories, buildTokenMap(categories));
2003
2015
  sendJson({
2004
2016
  categories,
2005
- tokenMap: resolvedTokenMap
2017
+ tokenMap: buildTokenMap(categories)
2006
2018
  });
2007
2019
  } catch (e) {
2008
2020
  sendError(e instanceof Error ? e.message : String(e));
@@ -2022,32 +2034,31 @@ async function handleTokensDelete(ctx, readBody, sendJson, sendError) {
2022
2034
  return;
2023
2035
  }
2024
2036
  const absoluteTokensPath = path.resolve(ctx.config.root, ctx.tokensPath);
2025
- const currentCategories = await parseTokens(absoluteTokensPath);
2026
- const currentMap = buildTokenMap(currentCategories);
2027
- const dependents = findDependentTokens(currentMap, dotPath);
2037
+ const dependents = findDependentTokens(buildTokenMap(await parseTokens(absoluteTokensPath)), dotPath);
2028
2038
  const rawData = await readRawTokenFile(absoluteTokensPath);
2029
- const deleted = deleteTokenAtPath(rawData, dotPath);
2030
- if (!deleted) {
2039
+ if (!deleteTokenAtPath(rawData, dotPath)) {
2031
2040
  sendError(`Token not found at path "${dotPath}"`, 404);
2032
2041
  return;
2033
2042
  }
2034
2043
  await writeRawTokenFile(absoluteTokensPath, rawData);
2035
2044
  const categories = await parseTokens(absoluteTokensPath);
2036
- const tokenMap = buildTokenMap(categories);
2037
- resolveReferences(categories, tokenMap);
2038
- const resolvedTokenMap = buildTokenMap(categories);
2045
+ resolveReferences(categories, buildTokenMap(categories));
2039
2046
  sendJson({
2040
2047
  categories,
2041
- tokenMap: resolvedTokenMap,
2048
+ tokenMap: buildTokenMap(categories),
2042
2049
  dependentsWarning: dependents.length > 0 ? dependents : void 0
2043
2050
  });
2044
2051
  } catch (e) {
2045
2052
  sendError(e instanceof Error ? e.message : String(e));
2046
2053
  }
2047
2054
  }
2048
-
2049
2055
  //#endregion
2050
2056
  //#region src/api-routes/handler-palette.ts
2057
+ /**
2058
+ * Palette handler for the Musea gallery API.
2059
+ *
2060
+ * Handles GET /api/arts/:path/palette endpoint.
2061
+ */
2051
2062
  /** GET /api/arts/:path/palette */
2052
2063
  async function handleArtPalette(ctx, match, sendJson, sendError) {
2053
2064
  const artPath = decodeURIComponent(match[1]);
@@ -2114,21 +2125,24 @@ async function handleArtPalette(ctx, match, sendJson, sendError) {
2114
2125
  sendError(e instanceof Error ? e.message : String(e));
2115
2126
  }
2116
2127
  }
2117
-
2118
2128
  //#endregion
2119
2129
  //#region src/api-routes/handlers.ts
2130
+ /**
2131
+ * Individual route handler functions for the Musea gallery API.
2132
+ *
2133
+ * Extracted from api-routes.ts to keep file sizes manageable.
2134
+ * These handle GET /api/arts/:path/... sub-routes.
2135
+ */
2120
2136
  /** GET /api/arts/:path/source */
2121
2137
  async function handleArtSource(ctx, match, sendJson, sendError) {
2122
2138
  const artPath = decodeURIComponent(match[1]);
2123
- const art = ctx.artFiles.get(artPath);
2124
- if (!art) {
2139
+ if (!ctx.artFiles.get(artPath)) {
2125
2140
  sendError("Art not found", 404);
2126
2141
  return;
2127
2142
  }
2128
2143
  try {
2129
- const source = await fs.promises.readFile(artPath, "utf-8");
2130
2144
  sendJson({
2131
- source,
2145
+ source: await fs.promises.readFile(artPath, "utf-8"),
2132
2146
  path: artPath
2133
2147
  });
2134
2148
  } catch (e) {
@@ -2148,13 +2162,8 @@ async function handleArtAnalysis(ctx, match, sendJson, sendError) {
2148
2162
  if (resolvedComponentPath) {
2149
2163
  const source = await fs.promises.readFile(resolvedComponentPath, "utf-8");
2150
2164
  const binding = loadNative();
2151
- if (binding.analyzeSfc) {
2152
- const analysis = binding.analyzeSfc(source, { filename: resolvedComponentPath });
2153
- sendJson(analysis);
2154
- } else {
2155
- const analysis = analyzeSfcFallback(source, { filename: resolvedComponentPath });
2156
- sendJson(analysis);
2157
- }
2165
+ if (binding.analyzeSfc) sendJson(binding.analyzeSfc(source, { filename: resolvedComponentPath }));
2166
+ else sendJson(analyzeSfcFallback(source, { filename: resolvedComponentPath }));
2158
2167
  } else sendJson({
2159
2168
  props: [],
2160
2169
  emits: []
@@ -2216,9 +2225,8 @@ async function handleArtDocs(ctx, match, sendJson, sendError) {
2216
2225
  /** GET /api/arts/:path/variants/:name/a11y */
2217
2226
  function handleArtA11y(ctx, match, sendJson, sendError) {
2218
2227
  const artPath = decodeURIComponent(match[1]);
2219
- const _variantName = decodeURIComponent(match[2]);
2220
- const art = ctx.artFiles.get(artPath);
2221
- if (!art) {
2228
+ decodeURIComponent(match[2]);
2229
+ if (!ctx.artFiles.get(artPath)) {
2222
2230
  sendError("Art not found", 404);
2223
2231
  return;
2224
2232
  }
@@ -2228,7 +2236,6 @@ function handleArtA11y(ctx, match, sendJson, sendError) {
2228
2236
  incomplete: 0
2229
2237
  });
2230
2238
  }
2231
-
2232
2239
  //#endregion
2233
2240
  //#region src/api-routes/post-handlers.ts
2234
2241
  /** POST /api/preview-with-props */
@@ -2245,8 +2252,7 @@ function handlePreviewWithProps(ctx, body, res, sendJson, sendError) {
2245
2252
  sendError("Variant not found", 404);
2246
2253
  return;
2247
2254
  }
2248
- const variantComponentName = toPascalCase(variant.name);
2249
- const moduleCode = generatePreviewModuleWithProps(art, variantComponentName, variant.name, propsOverride, ctx.resolvedPreviewCss, ctx.resolvedPreviewSetup);
2255
+ const moduleCode = generatePreviewModuleWithProps(art, toPascalCase(variant.name), variant.name, propsOverride, ctx.resolvedPreviewCss, ctx.resolvedPreviewSetup);
2250
2256
  res.setHeader("Content-Type", "application/javascript");
2251
2257
  res.end(moduleCode);
2252
2258
  } catch (e) {
@@ -2257,7 +2263,7 @@ function handlePreviewWithProps(ctx, body, res, sendJson, sendError) {
2257
2263
  async function handleGenerate(body, sendJson, sendError) {
2258
2264
  try {
2259
2265
  const { componentPath: reqComponentPath, options: autogenOptions } = JSON.parse(body);
2260
- const { generateArtFile: genArt } = await import("./autogen-Dx-SIBf_.js");
2266
+ const { generateArtFile: genArt } = await import("./autogen/index.mjs");
2261
2267
  const result = await genArt(reqComponentPath, autogenOptions);
2262
2268
  sendJson({
2263
2269
  generated: true,
@@ -2273,10 +2279,9 @@ async function handleGenerate(body, sendJson, sendError) {
2273
2279
  async function handleRunVrt(ctx, body, sendJson, sendError) {
2274
2280
  try {
2275
2281
  const { artPath, updateSnapshots } = JSON.parse(body);
2276
- const { MuseaVrtRunner: MuseaVrtRunner$1 } = await import("./vrt.js");
2277
- const runner = new MuseaVrtRunner$1({ snapshotDir: path.resolve(ctx.config.root, ".vize/snapshots") });
2278
- const port = ctx.getDevServerPort();
2279
- const baseUrl = `http://localhost:${port}`;
2282
+ const { MuseaVrtRunner } = await import("./vrt.mjs");
2283
+ const runner = new MuseaVrtRunner({ snapshotDir: path.resolve(ctx.config.root, ".vize/snapshots") });
2284
+ const baseUrl = `http://localhost:${ctx.getDevServerPort()}`;
2280
2285
  let artsToTest = Array.from(ctx.artFiles.values());
2281
2286
  if (artPath) artsToTest = artsToTest.filter((a) => a.path === artPath);
2282
2287
  await runner.start();
@@ -2300,7 +2305,6 @@ async function handleRunVrt(ctx, body, sendJson, sendError) {
2300
2305
  sendError(e instanceof Error ? e.message : String(e));
2301
2306
  }
2302
2307
  }
2303
-
2304
2308
  //#endregion
2305
2309
  //#region src/api-routes/index.ts
2306
2310
  /** Helper to read the full request body as a string. */
@@ -2356,12 +2360,10 @@ function createApiMiddleware(ctx) {
2356
2360
  return;
2357
2361
  }
2358
2362
  if (url?.startsWith("/arts/") && req.method === "PUT") {
2359
- const rest = url.slice(6);
2360
- const sourceMatch = rest.match(/^(.+)\/source$/);
2363
+ const sourceMatch = url.slice(6).match(/^(.+)\/source$/);
2361
2364
  if (sourceMatch) {
2362
2365
  const artPath = decodeURIComponent(sourceMatch[1]);
2363
- const art = ctx.artFiles.get(artPath);
2364
- if (!art) {
2366
+ if (!ctx.artFiles.get(artPath)) {
2365
2367
  sendError("Art not found", 404);
2366
2368
  return;
2367
2369
  }
@@ -2434,7 +2436,6 @@ function createApiMiddleware(ctx) {
2434
2436
  next();
2435
2437
  };
2436
2438
  }
2437
-
2438
2439
  //#endregion
2439
2440
  //#region src/manifest.ts
2440
2441
  /**
@@ -2444,17 +2445,22 @@ function generateManifestModule(artFiles) {
2444
2445
  const arts = Array.from(artFiles.values());
2445
2446
  return `export const arts = ${JSON.stringify(arts, null, 2)};`;
2446
2447
  }
2447
-
2448
2448
  //#endregion
2449
2449
  //#region src/plugin/virtual.ts
2450
+ /**
2451
+ * Virtual module handling for the Musea Vite plugin.
2452
+ *
2453
+ * Contains `resolveId`, `load`, and `handleHotUpdate` hooks that
2454
+ * manage virtual modules for gallery, manifest, preview, and art files.
2455
+ */
2450
2456
  const VIRTUAL_MUSEA_PREFIX = "\0musea:";
2451
2457
  const VIRTUAL_GALLERY = "\0musea-gallery";
2452
2458
  const VIRTUAL_MANIFEST = "\0musea-manifest";
2453
2459
  function createResolveId(state) {
2454
2460
  return function resolveId(id) {
2455
2461
  const root = state.getConfigRoot();
2456
- if (id === VIRTUAL_GALLERY) return VIRTUAL_GALLERY;
2457
- if (id === VIRTUAL_MANIFEST) return VIRTUAL_MANIFEST;
2462
+ if (id === "\0musea-gallery") return VIRTUAL_GALLERY;
2463
+ if (id === "\0musea-manifest") return VIRTUAL_MANIFEST;
2458
2464
  if (id.startsWith("virtual:musea-preview:")) return "\0musea-preview:" + id.slice(22);
2459
2465
  if (id.startsWith("virtual:musea-art:")) {
2460
2466
  const artPath = id.slice(18);
@@ -2473,8 +2479,8 @@ function createResolveId(state) {
2473
2479
  }
2474
2480
  function createLoad(state) {
2475
2481
  return function load(id) {
2476
- if (id === VIRTUAL_GALLERY) return generateGalleryModule(state.basePath);
2477
- if (id === VIRTUAL_MANIFEST) return generateManifestModule(state.artFiles);
2482
+ if (id === "\0musea-gallery") return generateGalleryModule(state.basePath);
2483
+ if (id === "\0musea-manifest") return generateManifestModule(state.artFiles);
2478
2484
  if (id.startsWith("\0musea-preview:")) {
2479
2485
  const rest = id.slice(15);
2480
2486
  const lastColonIndex = rest.lastIndexOf(":");
@@ -2482,10 +2488,7 @@ function createLoad(state) {
2482
2488
  const artPath = rest.slice(0, lastColonIndex);
2483
2489
  const variantName = rest.slice(lastColonIndex + 1);
2484
2490
  const art = state.artFiles.get(artPath);
2485
- if (art) {
2486
- const variantComponentName = toPascalCase(variantName);
2487
- return generatePreviewModule(art, variantComponentName, variantName, state.resolvedPreviewCss, state.resolvedPreviewSetup);
2488
- }
2491
+ if (art) return generatePreviewModule(art, toPascalCase(variantName), variantName, state.resolvedPreviewCss, state.resolvedPreviewSetup);
2489
2492
  }
2490
2493
  }
2491
2494
  if (id.startsWith("\0musea-art:")) {
@@ -2493,8 +2496,8 @@ function createLoad(state) {
2493
2496
  const art = state.artFiles.get(artPath);
2494
2497
  if (art) return generateArtModule(art, artPath);
2495
2498
  }
2496
- if (id.startsWith(VIRTUAL_MUSEA_PREFIX)) {
2497
- const realPath = id.slice(VIRTUAL_MUSEA_PREFIX.length).replace(/\?musea-virtual$/, "");
2499
+ if (id.startsWith("\0musea:")) {
2500
+ const realPath = id.slice(7).replace(/\?musea-virtual$/, "");
2498
2501
  const art = state.artFiles.get(realPath);
2499
2502
  if (art) return generateArtModule(art, realPath);
2500
2503
  }
@@ -2507,21 +2510,17 @@ function createHandleHotUpdate(state) {
2507
2510
  if (file.endsWith(".art.vue") && state.artFiles.has(file)) {
2508
2511
  await state.processArtFile(file);
2509
2512
  const virtualId = VIRTUAL_MUSEA_PREFIX + file + "?musea-virtual";
2510
- const server = state.getServer();
2511
- const modules = server?.moduleGraph.getModulesByFile(virtualId);
2513
+ const modules = state.getServer()?.moduleGraph.getModulesByFile(virtualId);
2512
2514
  if (modules) return [...modules];
2513
2515
  }
2514
2516
  if (state.inlineArt && file.endsWith(".vue") && !file.endsWith(".art.vue") && state.artFiles.has(file)) {
2515
2517
  await state.processArtFile(file);
2516
2518
  const virtualId = VIRTUAL_MUSEA_PREFIX + file;
2517
- const server = state.getServer();
2518
- const modules = server?.moduleGraph.getModulesByFile(virtualId);
2519
+ const modules = state.getServer()?.moduleGraph.getModulesByFile(virtualId);
2519
2520
  if (modules) return [...modules];
2520
2521
  }
2521
- return void 0;
2522
2522
  };
2523
2523
  }
2524
-
2525
2524
  //#endregion
2526
2525
  //#region src/plugin/index.ts
2527
2526
  /**
@@ -2540,7 +2539,7 @@ function musea(options = {}) {
2540
2539
  const previewSetup = options.previewSetup;
2541
2540
  let config;
2542
2541
  let server = null;
2543
- const artFiles = new Map();
2542
+ const artFiles = /* @__PURE__ */ new Map();
2544
2543
  let resolvedPreviewCss = [];
2545
2544
  let resolvedPreviewSetup = null;
2546
2545
  const virtualState = {
@@ -2555,9 +2554,6 @@ function musea(options = {}) {
2555
2554
  getServer: () => server,
2556
2555
  processArtFile
2557
2556
  };
2558
- const resolveId = createResolveId(virtualState);
2559
- const load = createLoad(virtualState);
2560
- const handleHotUpdate = createHandleHotUpdate(virtualState);
2561
2557
  const mainPlugin = {
2562
2558
  name: "vite-plugin-musea",
2563
2559
  enforce: "pre",
@@ -2607,8 +2603,7 @@ function musea(options = {}) {
2607
2603
  }
2608
2604
  if (inlineArt && file.endsWith(".vue") && !file.endsWith(".art.vue")) {
2609
2605
  const hadArt = artFiles.has(file);
2610
- const source = await fs.promises.readFile(file, "utf-8");
2611
- if (source.includes("<art")) {
2606
+ if ((await fs.promises.readFile(file, "utf-8")).includes("<art")) {
2612
2607
  await processArtFile(file);
2613
2608
  console.log(`[musea] Reloaded inline art: ${path.relative(config.root, file)}`);
2614
2609
  } else if (hadArt) {
@@ -2623,8 +2618,7 @@ function musea(options = {}) {
2623
2618
  console.log(`[musea] Added: ${path.relative(config.root, file)}`);
2624
2619
  }
2625
2620
  if (inlineArt && file.endsWith(".vue") && !file.endsWith(".art.vue")) {
2626
- const source = await fs.promises.readFile(file, "utf-8");
2627
- if (source.includes("<art")) {
2621
+ if ((await fs.promises.readFile(file, "utf-8")).includes("<art")) {
2628
2622
  await processArtFile(file);
2629
2623
  console.log(`[musea] Added inline art: ${path.relative(config.root, file)}`);
2630
2624
  }
@@ -2642,9 +2636,7 @@ function musea(options = {}) {
2642
2636
  if (address && typeof address === "object") {
2643
2637
  const protocol = devServer.config.server.https ? "https" : "http";
2644
2638
  const rawHost = address.address;
2645
- const host = rawHost === "::" || rawHost === "::1" || rawHost === "0.0.0.0" || rawHost === "127.0.0.1" ? "localhost" : rawHost;
2646
- const port = address.port;
2647
- const url = `${protocol}://${host}:${port}${basePath}`;
2639
+ const url = `${protocol}://${rawHost === "::" || rawHost === "::1" || rawHost === "0.0.0.0" || rawHost === "127.0.0.1" ? "localhost" : rawHost}:${address.port}${basePath}`;
2648
2640
  console.log();
2649
2641
  console.log(` \x1b[36m➜\x1b[0m \x1b[1mMusea Gallery:\x1b[0m \x1b[36m${url}\x1b[0m`);
2650
2642
  }
@@ -2658,15 +2650,14 @@ function musea(options = {}) {
2658
2650
  for (const file of files) await processArtFile(file);
2659
2651
  if (storybookCompat) await generateStorybookFiles(artFiles, config.root, storybookOutDir);
2660
2652
  },
2661
- resolveId,
2662
- load,
2663
- handleHotUpdate
2653
+ resolveId: createResolveId(virtualState),
2654
+ load: createLoad(virtualState),
2655
+ handleHotUpdate: createHandleHotUpdate(virtualState)
2664
2656
  };
2665
2657
  async function processArtFile(filePath) {
2666
2658
  try {
2667
2659
  const source = await fs.promises.readFile(filePath, "utf-8");
2668
- const binding = loadNative();
2669
- const parsed = binding.parseArt(source, { filename: filePath });
2660
+ const parsed = loadNative().parseArt(source, { filename: filePath });
2670
2661
  if (!parsed.variants || parsed.variants.length === 0) return;
2671
2662
  const isInline = !filePath.endsWith(".art.vue");
2672
2663
  const info = {
@@ -2700,11 +2691,10 @@ function musea(options = {}) {
2700
2691
  }
2701
2692
  return [mainPlugin];
2702
2693
  }
2703
-
2704
2694
  //#endregion
2705
2695
  //#region src/index.ts
2706
2696
  var src_default = musea;
2707
-
2708
2697
  //#endregion
2709
2698
  export { MuseaA11yRunner, MuseaVrtRunner, buildTokenMap, src_default as default, generateArtFile, generateTokensHtml, generateTokensMarkdown, generateVrtJsonReport, generateVrtReport, musea, parseTokens, processStyleDictionary, resolveReferences, scanTokenUsage, writeArtFile };
2710
- //# sourceMappingURL=index.js.map
2699
+
2700
+ //# sourceMappingURL=index.mjs.map