meno-core 1.0.52 → 1.0.53
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/build-astro.ts +183 -13
- package/build-next.ts +1361 -0
- package/build-static.ts +7 -5
- package/dist/bin/cli.js +2 -2
- package/dist/build-static.js +6 -6
- package/dist/chunks/{chunk-HNLUO36W.js → chunk-GZHGVVW3.js} +2 -2
- package/dist/chunks/chunk-GZHGVVW3.js.map +7 -0
- package/dist/chunks/{chunk-LPVETICS.js → chunk-H3GJ4H2U.js} +185 -1
- package/dist/chunks/chunk-H3GJ4H2U.js.map +7 -0
- package/dist/chunks/{chunk-CXCBV2M7.js → chunk-IGYR22T6.js} +76 -270
- package/dist/chunks/chunk-IGYR22T6.js.map +7 -0
- package/dist/chunks/{chunk-LHLHPYSP.js → chunk-JGP5A3Y5.js} +12 -11
- package/dist/chunks/chunk-JGP5A3Y5.js.map +7 -0
- package/dist/chunks/{chunk-7NIC4I3V.js → chunk-JGWFTO6P.js} +167 -21
- package/dist/chunks/chunk-JGWFTO6P.js.map +7 -0
- package/dist/chunks/{chunk-EDQSMAMP.js → chunk-O3NAGJP4.js} +85 -4
- package/dist/chunks/chunk-O3NAGJP4.js.map +7 -0
- package/dist/chunks/{chunk-H4JSCDNW.js → chunk-QB2LNO4W.js} +24 -1
- package/dist/chunks/chunk-QB2LNO4W.js.map +7 -0
- package/dist/chunks/{chunk-A725KYFK.js → chunk-R6XHAFBF.js} +561 -112
- package/dist/chunks/chunk-R6XHAFBF.js.map +7 -0
- package/dist/chunks/{chunk-J23ZX5AP.js → chunk-X754AHS5.js} +277 -1
- package/dist/chunks/chunk-X754AHS5.js.map +7 -0
- package/dist/chunks/{chunk-2QK6U5UK.js → chunk-YBLHKYFF.js} +12 -2
- package/dist/chunks/chunk-YBLHKYFF.js.map +7 -0
- package/dist/chunks/{constants-GWBAD66U.js → constants-STK2YBIW.js} +2 -2
- package/dist/entries/server-router.js +7 -7
- package/dist/lib/client/index.js +354 -59
- package/dist/lib/client/index.js.map +4 -4
- package/dist/lib/server/index.js +1458 -190
- package/dist/lib/server/index.js.map +4 -4
- package/dist/lib/shared/index.js +202 -34
- package/dist/lib/shared/index.js.map +4 -4
- package/dist/lib/test-utils/index.js +1 -1
- package/entries/client-router.tsx +5 -165
- package/lib/client/ErrorBoundary.test.tsx +27 -25
- package/lib/client/ErrorBoundary.tsx +34 -19
- package/lib/client/core/ComponentBuilder.ts +19 -2
- package/lib/client/core/builders/embedBuilder.ts +8 -4
- package/lib/client/core/builders/listBuilder.ts +23 -4
- package/lib/client/fontFamiliesService.test.ts +76 -0
- package/lib/client/fontFamiliesService.ts +69 -0
- package/lib/client/hmrCssReload.ts +160 -0
- package/lib/client/hooks/useColorVariables.ts +2 -0
- package/lib/client/index.ts +4 -0
- package/lib/client/meno-filter/ui.ts +2 -0
- package/lib/client/routing/RouteLoader.test.ts +2 -2
- package/lib/client/routing/RouteLoader.ts +8 -2
- package/lib/client/routing/Router.tsx +81 -15
- package/lib/client/scripts/ScriptExecutor.test.ts +143 -0
- package/lib/client/scripts/ScriptExecutor.ts +56 -2
- package/lib/client/styles/StyleInjector.ts +20 -5
- package/lib/client/styles/UtilityClassCollector.ts +7 -1
- package/lib/client/styles/cspNonce.test.ts +67 -0
- package/lib/client/styles/cspNonce.ts +63 -0
- package/lib/client/templateEngine.test.ts +80 -0
- package/lib/client/templateEngine.ts +5 -0
- package/lib/server/astro/cmsPageEmitter.ts +35 -5
- package/lib/server/astro/componentEmitter.ts +61 -5
- package/lib/server/astro/nodeToAstro.ts +149 -11
- package/lib/server/astro/normalizeOrphanTemplateProps.test.ts +264 -0
- package/lib/server/astro/normalizeOrphanTemplateProps.ts +184 -0
- package/lib/server/createServer.ts +11 -0
- package/lib/server/draftPageStore.ts +49 -0
- package/lib/server/fileWatcher.ts +62 -2
- package/lib/server/index.ts +13 -1
- package/lib/server/providers/fileSystemPageProvider.ts +8 -0
- package/lib/server/routes/api/components.ts +9 -4
- package/lib/server/routes/api/core-routes.ts +2 -2
- package/lib/server/routes/api/pages.ts +14 -22
- package/lib/server/routes/api/shared.ts +56 -0
- package/lib/server/routes/index.ts +90 -0
- package/lib/server/routes/pages.ts +13 -6
- package/lib/server/services/componentService.test.ts +199 -2
- package/lib/server/services/componentService.ts +354 -49
- package/lib/server/services/fileWatcherService.ts +4 -24
- package/lib/server/services/pageService.test.ts +23 -0
- package/lib/server/services/pageService.ts +124 -6
- package/lib/server/ssr/attributeBuilder.ts +8 -2
- package/lib/server/ssr/buildErrorOverlay.ts +1 -1
- package/lib/server/ssr/errorOverlay.test.ts +21 -2
- package/lib/server/ssr/errorOverlay.ts +38 -11
- package/lib/server/ssr/htmlGenerator.test.ts +53 -13
- package/lib/server/ssr/htmlGenerator.ts +71 -27
- package/lib/server/ssr/liveReloadIntegration.test.ts +123 -2
- package/lib/server/ssr/ssrRenderer.test.ts +67 -0
- package/lib/server/ssr/ssrRenderer.ts +94 -9
- package/lib/server/websocketManager.ts +0 -1
- package/lib/shared/componentRefs.ts +45 -0
- package/lib/shared/constants.ts +8 -0
- package/lib/shared/cssGeneration.ts +2 -0
- package/lib/shared/cssProperties.ts +184 -0
- package/lib/shared/expressionEvaluator.ts +54 -0
- package/lib/shared/fontCss.ts +101 -0
- package/lib/shared/fontLoader.ts +8 -86
- package/lib/shared/friendlyError.test.ts +87 -0
- package/lib/shared/friendlyError.ts +121 -0
- package/lib/shared/hrefRefs.test.ts +130 -0
- package/lib/shared/hrefRefs.ts +100 -0
- package/lib/shared/index.ts +52 -0
- package/lib/shared/inlineSvgStyleRules.test.ts +108 -0
- package/lib/shared/inlineSvgStyleRules.ts +134 -0
- package/lib/shared/interfaces/contentProvider.ts +13 -0
- package/lib/shared/itemTemplateUtils.test.ts +14 -0
- package/lib/shared/itemTemplateUtils.ts +4 -1
- package/lib/shared/registry/NodeTypeDefinition.ts +1 -1
- package/lib/shared/registry/nodeTypes/LinkNodeType.ts +1 -1
- package/lib/shared/slugTranslator.test.ts +24 -0
- package/lib/shared/slugTranslator.ts +24 -0
- package/lib/shared/styleNodeUtils.ts +4 -1
- package/lib/shared/tree/PathBuilder.test.ts +128 -1
- package/lib/shared/tree/PathBuilder.ts +83 -31
- package/lib/shared/types/comment.ts +99 -0
- package/lib/shared/types/index.ts +12 -0
- package/lib/shared/types/rendering.ts +8 -0
- package/lib/shared/utilityClassConfig.ts +4 -2
- package/lib/shared/utilityClassMapper.test.ts +24 -0
- package/lib/shared/validation/commentValidators.ts +69 -0
- package/lib/shared/validation/index.ts +1 -0
- package/lib/shared/viewportUnits.integration.test.ts +42 -0
- package/lib/shared/viewportUnits.test.ts +103 -0
- package/lib/shared/viewportUnits.ts +63 -0
- package/lib/test-utils/dom-setup.ts +6 -0
- package/package.json +1 -1
- package/dist/chunks/chunk-2QK6U5UK.js.map +0 -7
- package/dist/chunks/chunk-7NIC4I3V.js.map +0 -7
- package/dist/chunks/chunk-A725KYFK.js.map +0 -7
- package/dist/chunks/chunk-CXCBV2M7.js.map +0 -7
- package/dist/chunks/chunk-EDQSMAMP.js.map +0 -7
- package/dist/chunks/chunk-H4JSCDNW.js.map +0 -7
- package/dist/chunks/chunk-HNLUO36W.js.map +0 -7
- package/dist/chunks/chunk-J23ZX5AP.js.map +0 -7
- package/dist/chunks/chunk-LHLHPYSP.js.map +0 -7
- package/dist/chunks/chunk-LPVETICS.js.map +0 -7
- /package/dist/chunks/{constants-GWBAD66U.js.map → constants-STK2YBIW.js.map} +0 -0
package/dist/lib/client/index.js
CHANGED
|
@@ -2,6 +2,7 @@ import {
|
|
|
2
2
|
evaluateTemplate,
|
|
3
3
|
extractAttributesFromNode,
|
|
4
4
|
hasTemplates,
|
|
5
|
+
inlineSvgStyleRules,
|
|
5
6
|
isHtmlMapping,
|
|
6
7
|
isLinkMapping,
|
|
7
8
|
mergeNodeStyles,
|
|
@@ -12,12 +13,12 @@ import {
|
|
|
12
13
|
resolveLinkMapping,
|
|
13
14
|
resolveStyleMapping,
|
|
14
15
|
skipEmptyTemplateAttributes
|
|
15
|
-
} from "../../chunks/chunk-
|
|
16
|
+
} from "../../chunks/chunk-O3NAGJP4.js";
|
|
16
17
|
import {
|
|
17
18
|
filterCSSProperties,
|
|
18
19
|
logNetworkError,
|
|
19
20
|
logRuntimeError
|
|
20
|
-
} from "../../chunks/chunk-
|
|
21
|
+
} from "../../chunks/chunk-H3GJ4H2U.js";
|
|
21
22
|
import {
|
|
22
23
|
BaseComponentRegistry,
|
|
23
24
|
DEFAULT_PREFETCH_CONFIG,
|
|
@@ -55,11 +56,13 @@ import {
|
|
|
55
56
|
resolveItemsTemplate,
|
|
56
57
|
resolvePropsFromDefinition,
|
|
57
58
|
responsiveStylesToClasses,
|
|
59
|
+
rewriteViewportUnits,
|
|
58
60
|
setGlobalTemplateContext,
|
|
59
61
|
singularize,
|
|
60
62
|
sortClassesByPropertyOrder,
|
|
63
|
+
toFriendlyError,
|
|
61
64
|
validatePageData
|
|
62
|
-
} from "../../chunks/chunk-
|
|
65
|
+
} from "../../chunks/chunk-JGWFTO6P.js";
|
|
63
66
|
import {
|
|
64
67
|
DEFAULT_BREAKPOINTS,
|
|
65
68
|
DEFAULT_I18N_CONFIG,
|
|
@@ -84,7 +87,7 @@ import {
|
|
|
84
87
|
NOT_FOUND_TIMEOUT_MS,
|
|
85
88
|
RAW_HTML_PREFIX,
|
|
86
89
|
init_constants
|
|
87
|
-
} from "../../chunks/chunk-
|
|
90
|
+
} from "../../chunks/chunk-YBLHKYFF.js";
|
|
88
91
|
import "../../chunks/chunk-KSBZ2L7C.js";
|
|
89
92
|
|
|
90
93
|
// lib/client/core/ComponentBuilder.ts
|
|
@@ -129,6 +132,9 @@ var ErrorBoundary = class extends Component {
|
|
|
129
132
|
if (fallback) {
|
|
130
133
|
return fallback(error, errorInfo);
|
|
131
134
|
}
|
|
135
|
+
const friendly = toFriendlyError(error);
|
|
136
|
+
const friendlyMessage = friendly.friendlyMessage.replace(/`/g, "");
|
|
137
|
+
const friendlyHint = friendly.hint?.replace(/`/g, "");
|
|
132
138
|
if (level === "page") {
|
|
133
139
|
return h(
|
|
134
140
|
"div",
|
|
@@ -157,7 +163,7 @@ var ErrorBoundary = class extends Component {
|
|
|
157
163
|
fontSize: "24px",
|
|
158
164
|
fontWeight: "600"
|
|
159
165
|
}
|
|
160
|
-
},
|
|
166
|
+
}, `\u26A0\uFE0F ${friendly.title}`),
|
|
161
167
|
h("p", {
|
|
162
168
|
style: {
|
|
163
169
|
margin: "0 0 16px 0",
|
|
@@ -165,21 +171,8 @@ var ErrorBoundary = class extends Component {
|
|
|
165
171
|
fontSize: "16px",
|
|
166
172
|
lineHeight: "1.5"
|
|
167
173
|
}
|
|
168
|
-
},
|
|
169
|
-
h(
|
|
170
|
-
style: {
|
|
171
|
-
background: "#fff",
|
|
172
|
-
border: "1px solid #ddd",
|
|
173
|
-
borderRadius: "4px",
|
|
174
|
-
padding: "16px",
|
|
175
|
-
marginBottom: "16px",
|
|
176
|
-
fontFamily: "monospace",
|
|
177
|
-
fontSize: "14px",
|
|
178
|
-
color: "#c00",
|
|
179
|
-
overflowX: "auto"
|
|
180
|
-
}
|
|
181
|
-
}, error.message),
|
|
182
|
-
process.env.NODE_ENV === "development" && errorInfo?.componentStack && h(
|
|
174
|
+
}, friendlyHint ? `${friendlyMessage} ${friendlyHint}` : friendlyMessage),
|
|
175
|
+
h(
|
|
183
176
|
"details",
|
|
184
177
|
{
|
|
185
178
|
style: {
|
|
@@ -194,8 +187,21 @@ var ErrorBoundary = class extends Component {
|
|
|
194
187
|
fontWeight: "600",
|
|
195
188
|
marginBottom: "8px"
|
|
196
189
|
}
|
|
197
|
-
}, "
|
|
198
|
-
h("
|
|
190
|
+
}, "Technical details"),
|
|
191
|
+
h("div", {
|
|
192
|
+
style: {
|
|
193
|
+
background: "#fff",
|
|
194
|
+
border: "1px solid #ddd",
|
|
195
|
+
borderRadius: "4px",
|
|
196
|
+
padding: "16px",
|
|
197
|
+
margin: "8px 0",
|
|
198
|
+
fontFamily: "monospace",
|
|
199
|
+
fontSize: "14px",
|
|
200
|
+
color: "#c00",
|
|
201
|
+
overflowX: "auto"
|
|
202
|
+
}
|
|
203
|
+
}, error.message),
|
|
204
|
+
process.env.NODE_ENV === "development" && errorInfo?.componentStack && h("pre", {
|
|
199
205
|
style: {
|
|
200
206
|
background: "#f5f5f5",
|
|
201
207
|
border: "1px solid #ddd",
|
|
@@ -256,10 +262,18 @@ var ErrorBoundary = class extends Component {
|
|
|
256
262
|
color: "#c00",
|
|
257
263
|
fontSize: "14px"
|
|
258
264
|
}
|
|
259
|
-
},
|
|
265
|
+
}, `${friendly.title}${componentName ? ` (${componentName})` : ""}`)
|
|
260
266
|
),
|
|
261
267
|
h("div", {
|
|
262
268
|
style: {
|
|
269
|
+
fontSize: "13px",
|
|
270
|
+
color: "#666",
|
|
271
|
+
lineHeight: "1.5"
|
|
272
|
+
}
|
|
273
|
+
}, friendlyHint ? `${friendlyMessage} ${friendlyHint}` : friendlyMessage),
|
|
274
|
+
process.env.NODE_ENV === "development" && h("div", {
|
|
275
|
+
style: {
|
|
276
|
+
marginTop: "8px",
|
|
263
277
|
fontSize: "12px",
|
|
264
278
|
color: "#666",
|
|
265
279
|
fontFamily: "monospace",
|
|
@@ -467,6 +481,29 @@ async function initializeBreakpoints(forceRefresh = false) {
|
|
|
467
481
|
}
|
|
468
482
|
var initializeConfig = initializeBreakpoints;
|
|
469
483
|
|
|
484
|
+
// lib/client/styles/cspNonce.ts
|
|
485
|
+
var cached;
|
|
486
|
+
function getCspNonce() {
|
|
487
|
+
if (cached !== void 0) return cached;
|
|
488
|
+
if (typeof document === "undefined") {
|
|
489
|
+
cached = null;
|
|
490
|
+
return cached;
|
|
491
|
+
}
|
|
492
|
+
try {
|
|
493
|
+
const meta = document.querySelector('meta[name="csp-nonce"]');
|
|
494
|
+
cached = meta?.getAttribute("content") ?? null;
|
|
495
|
+
} catch {
|
|
496
|
+
cached = null;
|
|
497
|
+
}
|
|
498
|
+
return cached;
|
|
499
|
+
}
|
|
500
|
+
function applyNonce(el) {
|
|
501
|
+
const n = getCspNonce();
|
|
502
|
+
if (n) {
|
|
503
|
+
el.nonce = n;
|
|
504
|
+
}
|
|
505
|
+
}
|
|
506
|
+
|
|
470
507
|
// lib/client/styles/UtilityClassCollector.ts
|
|
471
508
|
function buildResponsivePrefixMap(breakpoints) {
|
|
472
509
|
const breakpointValues = getBreakpointValues(breakpoints);
|
|
@@ -531,6 +568,7 @@ var UtilityClassCollectorImpl = class {
|
|
|
531
568
|
if (document.head) {
|
|
532
569
|
this.styleEl = document.createElement("style");
|
|
533
570
|
this.styleEl.id = "utility-css";
|
|
571
|
+
applyNonce(this.styleEl);
|
|
534
572
|
document.head.appendChild(this.styleEl);
|
|
535
573
|
}
|
|
536
574
|
return this.styleEl;
|
|
@@ -554,7 +592,7 @@ var UtilityClassCollectorImpl = class {
|
|
|
554
592
|
if (this.injectedRules.has(name)) continue;
|
|
555
593
|
const css = generateSingleClassCSS(name, breakpointConfig2, responsiveScalesConfig2, remConversionConfig2);
|
|
556
594
|
if (css) {
|
|
557
|
-
this.injectedRules.set(name, css);
|
|
595
|
+
this.injectedRules.set(name, rewriteViewportUnits(css));
|
|
558
596
|
hasNew = true;
|
|
559
597
|
}
|
|
560
598
|
}
|
|
@@ -706,8 +744,8 @@ function hasCMSTemplate(text) {
|
|
|
706
744
|
import { createElement as h2 } from "react";
|
|
707
745
|
import DOMPurify from "isomorphic-dompurify";
|
|
708
746
|
var SANITIZE_CONFIG = {
|
|
709
|
-
ALLOWED_TAGS: ["svg", "path", "circle", "rect", "line", "polyline", "polygon", "g", "text", "tspan", "image", "defs", "use", "linearGradient", "radialGradient", "stop", "clipPath", "mask", "pattern", "marker", "symbol", "a", "div", "span", "p", "br", "button", "img", "iframe", "video", "audio", "source", "canvas", "b", "i", "u", "strong", "em", "sub", "sup", "mark", "s", "small", "del", "ins", "q", "abbr", "code", "pre", "blockquote", "ul", "ol", "li", "h1", "h2", "h3", "h4", "h5", "h6", "style", "animate", "animateTransform", "animateMotion", "set"],
|
|
710
|
-
ALLOWED_ATTR: ["class", "id", "style", "width", "height", "viewBox", "xmlns", "fill", "stroke", "stroke-width", "stroke-linecap", "stroke-linejoin", "stroke-dasharray", "stroke-dashoffset", "d", "cx", "cy", "r", "x", "y", "x1", "y1", "x2", "y2", "points", "href", "src", "alt", "target", "rel", "data-*", "aria-*", "transform", "opacity", "fill-opacity", "stroke-opacity", "font-size", "font-family", "text-anchor", "dominant-baseline", "offset", "stop-color", "stop-opacity", "frameborder", "allowfullscreen", "allow", "title", "attributeName", "values", "dur", "begin", "end", "repeatCount", "repeatDur", "keyTimes", "keySplines", "calcMode", "from", "to", "by", "additive", "accumulate", "type", "rotate", "keyPoints", "path"],
|
|
747
|
+
ALLOWED_TAGS: ["svg", "path", "circle", "rect", "line", "polyline", "polygon", "g", "text", "tspan", "image", "defs", "use", "linearGradient", "radialGradient", "stop", "clipPath", "mask", "pattern", "marker", "symbol", "a", "div", "span", "p", "br", "button", "img", "iframe", "video", "audio", "source", "canvas", "b", "i", "u", "strong", "em", "sub", "sup", "mark", "s", "small", "del", "ins", "q", "abbr", "code", "pre", "blockquote", "ul", "ol", "li", "h1", "h2", "h3", "h4", "h5", "h6", "style", "animate", "animateTransform", "animateMotion", "set", "filter", "feGaussianBlur", "feOffset", "feMerge", "feMergeNode", "feColorMatrix", "feComposite", "feFlood", "feMorphology", "feBlend", "feDropShadow", "feTurbulence", "feDisplacementMap", "foreignObject"],
|
|
748
|
+
ALLOWED_ATTR: ["class", "id", "style", "width", "height", "viewBox", "xmlns", "xmlns:xlink", "xlink:href", "fill", "stroke", "stroke-width", "stroke-linecap", "stroke-linejoin", "stroke-dasharray", "stroke-dashoffset", "d", "cx", "cy", "r", "x", "y", "x1", "y1", "x2", "y2", "points", "href", "src", "alt", "target", "rel", "data-*", "aria-*", "transform", "opacity", "fill-opacity", "fill-rule", "clip-rule", "clip-path", "clipPathUnits", "mask", "mask-type", "maskUnits", "maskContentUnits", "patternUnits", "patternContentUnits", "patternTransform", "gradientUnits", "gradientTransform", "spreadMethod", "preserveAspectRatio", "marker-start", "marker-mid", "marker-end", "markerUnits", "markerWidth", "markerHeight", "refX", "refY", "orient", "paint-order", "vector-effect", "filter", "filterUnits", "primitiveUnits", "in", "in2", "result", "stdDeviation", "flood-color", "flood-opacity", "stroke-opacity", "font-size", "font-family", "font-weight", "font-style", "text-anchor", "dominant-baseline", "offset", "stop-color", "stop-opacity", "frameborder", "allowfullscreen", "allow", "title", "attributeName", "values", "dur", "begin", "end", "repeatCount", "repeatDur", "keyTimes", "keySplines", "calcMode", "from", "to", "by", "additive", "accumulate", "type", "rotate", "keyPoints", "path"],
|
|
711
749
|
KEEP_CONTENT: true
|
|
712
750
|
};
|
|
713
751
|
function buildEmbed(node, ctx, deps) {
|
|
@@ -723,7 +761,7 @@ function buildEmbed(node, ctx, deps) {
|
|
|
723
761
|
const effectiveLocale = ctx.cmsLocale || ctx.locale;
|
|
724
762
|
htmlContent = processCMSTemplate(htmlContent, ctx.cmsContext, effectiveLocale);
|
|
725
763
|
}
|
|
726
|
-
const sanitizedHtml = DOMPurify.sanitize(htmlContent, SANITIZE_CONFIG);
|
|
764
|
+
const sanitizedHtml = inlineSvgStyleRules(DOMPurify.sanitize(htmlContent, SANITIZE_CONFIG));
|
|
727
765
|
const effectiveParentComponentName = deps.getEffectiveParentComponentName(componentContext, parentComponentName);
|
|
728
766
|
const extractedAttributes = extractAttributesFromNode(node);
|
|
729
767
|
const embedProps = {
|
|
@@ -1229,6 +1267,15 @@ function buildList(node, children, ctx, deps) {
|
|
|
1229
1267
|
containerProps["data-list"] = "true";
|
|
1230
1268
|
containerProps["data-source"] = source || (sourceIsResolved ? "resolved" : "");
|
|
1231
1269
|
}
|
|
1270
|
+
if (cmsItemIndexPath && cmsItemIndexPath.length > 0) {
|
|
1271
|
+
containerProps["data-cms-item-index"] = cmsItemIndexPath.join(".");
|
|
1272
|
+
if (cmsListPaths && cmsListPaths.length === cmsItemIndexPath.length) {
|
|
1273
|
+
containerProps["data-cms-context"] = JSON.stringify({
|
|
1274
|
+
itemIndexPath: cmsItemIndexPath,
|
|
1275
|
+
listPaths: cmsListPaths
|
|
1276
|
+
});
|
|
1277
|
+
}
|
|
1278
|
+
}
|
|
1232
1279
|
if (Object.keys(extractedAttributes).length > 0) {
|
|
1233
1280
|
Object.assign(containerProps, extractedAttributes);
|
|
1234
1281
|
}
|
|
@@ -1330,17 +1377,19 @@ function buildList(node, children, ctx, deps) {
|
|
|
1330
1377
|
templateContext: itemTemplateContext,
|
|
1331
1378
|
componentResolvedProps
|
|
1332
1379
|
});
|
|
1380
|
+
const cmsItem = item;
|
|
1381
|
+
const itemKey = cmsItem?._id ?? cmsItem?._filename ?? index;
|
|
1333
1382
|
if (itemChildren === null) continue;
|
|
1334
1383
|
if (Array.isArray(itemChildren)) {
|
|
1335
1384
|
for (const child of itemChildren) {
|
|
1336
1385
|
if (typeof child === "object" && child !== null && "key" in child) {
|
|
1337
|
-
renderedItems.push({ ...child, key: `${child.key}-item-${
|
|
1386
|
+
renderedItems.push({ ...child, key: `${child.key}-item-${itemKey}` });
|
|
1338
1387
|
} else {
|
|
1339
1388
|
renderedItems.push(child);
|
|
1340
1389
|
}
|
|
1341
1390
|
}
|
|
1342
1391
|
} else if (typeof itemChildren === "object" && itemChildren !== null && "key" in itemChildren) {
|
|
1343
|
-
renderedItems.push({ ...itemChildren, key: `${itemChildren.key}-item-${
|
|
1392
|
+
renderedItems.push({ ...itemChildren, key: `${itemChildren.key}-item-${itemKey}` });
|
|
1344
1393
|
} else {
|
|
1345
1394
|
renderedItems.push(itemChildren);
|
|
1346
1395
|
}
|
|
@@ -1679,18 +1728,18 @@ var ComponentBuilder = class {
|
|
|
1679
1728
|
* Get cached utility classes for a style object
|
|
1680
1729
|
*/
|
|
1681
1730
|
getCachedStyleClasses(style) {
|
|
1682
|
-
let
|
|
1683
|
-
if (!
|
|
1731
|
+
let cached2 = this.styleClassCache.get(style);
|
|
1732
|
+
if (!cached2) {
|
|
1684
1733
|
const scales = getCachedResponsiveScalesConfig();
|
|
1685
1734
|
const fluidActive = scales?.enabled === true && scales?.mode === "fluid";
|
|
1686
|
-
|
|
1735
|
+
cached2 = responsiveStylesToClasses(
|
|
1687
1736
|
style,
|
|
1688
1737
|
{ fluidActive, responsiveScales: scales ?? void 0 }
|
|
1689
1738
|
);
|
|
1690
|
-
this.styleClassCache.set(style,
|
|
1739
|
+
this.styleClassCache.set(style, cached2);
|
|
1691
1740
|
}
|
|
1692
|
-
UtilityClassCollector.collect(
|
|
1693
|
-
return
|
|
1741
|
+
UtilityClassCollector.collect(cached2);
|
|
1742
|
+
return cached2;
|
|
1694
1743
|
}
|
|
1695
1744
|
/**
|
|
1696
1745
|
* Helper function to create onClick handlers from JSON-defined onClick values
|
|
@@ -1861,6 +1910,9 @@ var ComponentBuilder = class {
|
|
|
1861
1910
|
componentResolvedProps = null
|
|
1862
1911
|
} = options;
|
|
1863
1912
|
if (!node) return null;
|
|
1913
|
+
if (typeof node === "object" && node._code === true) {
|
|
1914
|
+
return null;
|
|
1915
|
+
}
|
|
1864
1916
|
if (isI18nValue(node)) {
|
|
1865
1917
|
const i18nResolveConfig = i18nConfig ?? DEFAULT_I18N_CONFIG;
|
|
1866
1918
|
const i18nEffectiveLocale = locale || i18nResolveConfig.defaultLocale;
|
|
@@ -2267,7 +2319,12 @@ var ComponentBuilder = class {
|
|
|
2267
2319
|
itemContext = null,
|
|
2268
2320
|
cmsItemIndexPath = null,
|
|
2269
2321
|
cmsListPaths = null,
|
|
2270
|
-
templateContext = null
|
|
2322
|
+
templateContext = null,
|
|
2323
|
+
// The host (outer) component's resolved props. Forwarded to
|
|
2324
|
+
// `processStructure` as `parentProps` so a `{{x}}` in this
|
|
2325
|
+
// component's structure falls back to the host's `x` when this
|
|
2326
|
+
// component's interface doesn't declare it.
|
|
2327
|
+
componentResolvedProps: parentResolvedProps = null
|
|
2271
2328
|
} = options;
|
|
2272
2329
|
const componentDef = this.componentRegistry.get(componentName);
|
|
2273
2330
|
if (!componentDef) return null;
|
|
@@ -2298,7 +2355,11 @@ var ComponentBuilder = class {
|
|
|
2298
2355
|
const markedChildren = typedChildren ? markAsSlotContent(typedChildren) : void 0;
|
|
2299
2356
|
const processedStructure = processStructure(
|
|
2300
2357
|
structuredComponentDef.structure,
|
|
2301
|
-
{
|
|
2358
|
+
{
|
|
2359
|
+
props: resolvedProps,
|
|
2360
|
+
componentDef: structuredComponentDef,
|
|
2361
|
+
parentProps: parentResolvedProps ?? void 0
|
|
2362
|
+
},
|
|
2302
2363
|
viewportWidth,
|
|
2303
2364
|
markedChildren
|
|
2304
2365
|
);
|
|
@@ -2523,7 +2584,7 @@ var RouteLoader = class {
|
|
|
2523
2584
|
*/
|
|
2524
2585
|
async loadGlobalComponents(signal) {
|
|
2525
2586
|
try {
|
|
2526
|
-
const fetchOptions = { cache: "
|
|
2587
|
+
const fetchOptions = { cache: "default" };
|
|
2527
2588
|
if (signal) {
|
|
2528
2589
|
fetchOptions.signal = signal;
|
|
2529
2590
|
}
|
|
@@ -2586,10 +2647,10 @@ var RouteLoader = class {
|
|
|
2586
2647
|
if (this.config.onLocaleDetected && !this.isCancelled) {
|
|
2587
2648
|
this.config.onLocaleDetected(locale);
|
|
2588
2649
|
}
|
|
2589
|
-
const
|
|
2590
|
-
if (
|
|
2650
|
+
const cached2 = this.prefetchService?.getFromCache(pathWithoutLocale);
|
|
2651
|
+
if (cached2) {
|
|
2591
2652
|
let tree2 = null;
|
|
2592
|
-
const parsed2 =
|
|
2653
|
+
const parsed2 = cached2.data;
|
|
2593
2654
|
if (parsed2.components) {
|
|
2594
2655
|
this.config.componentRegistry.merge(parsed2.components);
|
|
2595
2656
|
tree2 = parsed2.root || parsed2;
|
|
@@ -2606,7 +2667,7 @@ var RouteLoader = class {
|
|
|
2606
2667
|
return tree2;
|
|
2607
2668
|
}
|
|
2608
2669
|
const response = await fetch(`${API_ROUTES.PAGE_CONTENT}?page=${encodeURIComponent(pathWithoutLocale)}`, {
|
|
2609
|
-
cache: "
|
|
2670
|
+
cache: "default",
|
|
2610
2671
|
signal: abortController.signal
|
|
2611
2672
|
});
|
|
2612
2673
|
if (abortController.signal.aborted || this.isCancelled) {
|
|
@@ -3235,15 +3296,17 @@ ${originalCSS}`);
|
|
|
3235
3296
|
}
|
|
3236
3297
|
}
|
|
3237
3298
|
if (processedCSSBlocks.length === 0) return;
|
|
3238
|
-
const combinedCSS = processedCSSBlocks.join("\n\n");
|
|
3299
|
+
const combinedCSS = rewriteViewportUnits(processedCSSBlocks.join("\n\n"));
|
|
3239
3300
|
const hash = simpleHash(combinedCSS);
|
|
3240
|
-
|
|
3301
|
+
const existing = typeof document !== "undefined" ? document.getElementById(this.styleId) : null;
|
|
3302
|
+
if (hash === this.previousComponentCSSHash && existing) return;
|
|
3241
3303
|
this.previousComponentCSSHash = hash;
|
|
3242
3304
|
if (document.head) {
|
|
3243
|
-
let styleTag =
|
|
3305
|
+
let styleTag = existing;
|
|
3244
3306
|
if (!styleTag) {
|
|
3245
3307
|
styleTag = document.createElement("style");
|
|
3246
3308
|
styleTag.id = this.styleId;
|
|
3309
|
+
applyNonce(styleTag);
|
|
3247
3310
|
document.head.appendChild(styleTag);
|
|
3248
3311
|
}
|
|
3249
3312
|
styleTag.textContent = combinedCSS;
|
|
@@ -3261,13 +3324,16 @@ ${originalCSS}`);
|
|
|
3261
3324
|
const breakpointConfig2 = getCachedBreakpointConfig() || DEFAULT_BREAKPOINTS;
|
|
3262
3325
|
const remConversionConfig2 = getCachedRemConversionConfig() || void 0;
|
|
3263
3326
|
const responsiveScalesConfig2 = getCachedResponsiveScalesConfig() || void 0;
|
|
3264
|
-
const interactiveCSS =
|
|
3327
|
+
const interactiveCSS = rewriteViewportUnits(
|
|
3328
|
+
generateAllInteractiveCSS(interactiveStylesMap, breakpointConfig2, remConversionConfig2, responsiveScalesConfig2)
|
|
3329
|
+
);
|
|
3265
3330
|
if (!interactiveCSS) return;
|
|
3266
3331
|
if (document.head) {
|
|
3267
3332
|
let styleTag = document.getElementById(interactiveStyleId);
|
|
3268
3333
|
if (!styleTag) {
|
|
3269
3334
|
styleTag = document.createElement("style");
|
|
3270
3335
|
styleTag.id = interactiveStyleId;
|
|
3336
|
+
applyNonce(styleTag);
|
|
3271
3337
|
document.head.appendChild(styleTag);
|
|
3272
3338
|
}
|
|
3273
3339
|
styleTag.textContent = interactiveCSS;
|
|
@@ -3308,9 +3374,33 @@ function generateDestructure(defineVars, interfaceDef) {
|
|
|
3308
3374
|
var ScriptExecutor = class {
|
|
3309
3375
|
componentRegistry;
|
|
3310
3376
|
elementRegistry;
|
|
3377
|
+
// Tracks which (element, componentName) pairs have already had their user
|
|
3378
|
+
// JS executed. Prevents stacking side effects (IntersectionObservers,
|
|
3379
|
+
// event listeners, intervals) when execute() is re-called on the same
|
|
3380
|
+
// DOM nodes after a structural commit. WeakMap stays out of the DOM and
|
|
3381
|
+
// GCs cleanly when React unmounts elements.
|
|
3382
|
+
boundElements = /* @__PURE__ */ new WeakMap();
|
|
3311
3383
|
constructor(config) {
|
|
3312
3384
|
this.componentRegistry = config.componentRegistry;
|
|
3313
3385
|
this.elementRegistry = config.elementRegistry;
|
|
3386
|
+
if (typeof window !== "undefined") {
|
|
3387
|
+
window.__menoShouldBind = (el, name) => this.shouldBind(el, name);
|
|
3388
|
+
}
|
|
3389
|
+
}
|
|
3390
|
+
/**
|
|
3391
|
+
* Check whether (element, componentName) has already been bound this
|
|
3392
|
+
* session. Records the bind on first call. Returns `true` if the caller
|
|
3393
|
+
* should run the user JS, `false` if it should skip.
|
|
3394
|
+
*/
|
|
3395
|
+
shouldBind(el, componentName) {
|
|
3396
|
+
let names = this.boundElements.get(el);
|
|
3397
|
+
if (names && names.has(componentName)) return false;
|
|
3398
|
+
if (!names) {
|
|
3399
|
+
names = /* @__PURE__ */ new Set();
|
|
3400
|
+
this.boundElements.set(el, names);
|
|
3401
|
+
}
|
|
3402
|
+
names.add(componentName);
|
|
3403
|
+
return true;
|
|
3314
3404
|
}
|
|
3315
3405
|
/**
|
|
3316
3406
|
* Execute JavaScript code via new Function() with error isolation
|
|
@@ -3350,6 +3440,10 @@ var ScriptExecutor = class {
|
|
|
3350
3440
|
if (!props) {
|
|
3351
3441
|
return;
|
|
3352
3442
|
}
|
|
3443
|
+
const instanceEl = this.elementRegistry.get(rootPath);
|
|
3444
|
+
if (instanceEl && !this.shouldBind(instanceEl, componentName)) {
|
|
3445
|
+
return;
|
|
3446
|
+
}
|
|
3353
3447
|
try {
|
|
3354
3448
|
const processedJS = processCodeTemplates(originalJS, props);
|
|
3355
3449
|
this.executeWrappedJS(processedJS, `${componentName} (instance: ${rootPath})`);
|
|
@@ -3375,10 +3469,20 @@ var ScriptExecutor = class {
|
|
|
3375
3469
|
// Component: ${componentName} (defineVars)
|
|
3376
3470
|
try {
|
|
3377
3471
|
var elements = document.querySelectorAll('[data-component~="${componentName}"]');
|
|
3472
|
+
var shouldBind = (typeof window !== 'undefined' && typeof window.__menoShouldBind === 'function')
|
|
3473
|
+
? window.__menoShouldBind
|
|
3474
|
+
: null;
|
|
3378
3475
|
elements.forEach(function(el) {
|
|
3476
|
+
// Skip elements already bound for this component. When the host
|
|
3477
|
+
// hook is absent (direct <script> use, test harness), bind
|
|
3478
|
+
// unconditionally \u2014 preserves legacy "runs once at page load"
|
|
3479
|
+
// semantics for non-runtime contexts.
|
|
3480
|
+
if (shouldBind && !shouldBind(el, ${JSON.stringify(componentName)})) {
|
|
3481
|
+
return;
|
|
3482
|
+
}
|
|
3379
3483
|
var propsStr = el.getAttribute('data-props');
|
|
3380
3484
|
var allProps = propsStr ? JSON.parse(propsStr) : {};
|
|
3381
|
-
var props = allProps[
|
|
3485
|
+
var props = allProps[${JSON.stringify(componentName)}] || {};
|
|
3382
3486
|
(function(el, props) {
|
|
3383
3487
|
${destructure}
|
|
3384
3488
|
${js}
|
|
@@ -3478,7 +3582,12 @@ var ScriptExecutor = class {
|
|
|
3478
3582
|
}
|
|
3479
3583
|
/**
|
|
3480
3584
|
* Re-execute JavaScript for a specific element instance (used for editor reactivity)
|
|
3481
|
-
* Updates data-props attribute and re-runs the component JS for that element
|
|
3585
|
+
* Updates data-props attribute and re-runs the component JS for that element.
|
|
3586
|
+
*
|
|
3587
|
+
* NOTE: This path intentionally bypasses the per-element bind dedup
|
|
3588
|
+
* (`boundElements` / `shouldBind`). It exists so live prop edits in the
|
|
3589
|
+
* editor can re-run the user JS on demand with new prop values — the
|
|
3590
|
+
* caller is signaling "re-bind this element now," not "bind once."
|
|
3482
3591
|
* @param componentName - Component name
|
|
3483
3592
|
* @param element - The DOM element to re-execute for
|
|
3484
3593
|
* @param newProps - New props to inject
|
|
@@ -3858,6 +3967,7 @@ function Router(props = {}) {
|
|
|
3858
3967
|
const [cmsTemplatePath, setCmsTemplatePath] = useState2(null);
|
|
3859
3968
|
const lastCommitTimestampRef = useRef2(0);
|
|
3860
3969
|
const COMMIT_GRACE_MS = 1e3;
|
|
3970
|
+
const lastCommitStructureChangedRef = useRef2(true);
|
|
3861
3971
|
const ssrCmsHandledRef = useRef2(false);
|
|
3862
3972
|
const initialLoadDoneRef = useRef2(false);
|
|
3863
3973
|
const routeLoader = useRef2(new RouteLoader({
|
|
@@ -3934,29 +4044,51 @@ function Router(props = {}) {
|
|
|
3934
4044
|
useEffect2(() => {
|
|
3935
4045
|
if (typeof window === "undefined") return;
|
|
3936
4046
|
const handleMessage = (event) => {
|
|
3937
|
-
if (event.data?.type === IFRAME_MESSAGE_TYPES.CSS_VARIABLE_UPDATE) {
|
|
3938
|
-
const { name, value } = event.data;
|
|
3939
|
-
|
|
4047
|
+
if (event.data?.type === IFRAME_MESSAGE_TYPES.CSS_VARIABLE_UPDATE || event.data?.type === IFRAME_MESSAGE_TYPES.CSS_VARIABLE_SCOPED_UPDATE) {
|
|
4048
|
+
const { name, value, media, maxWidth } = event.data;
|
|
4049
|
+
const styleId = "meno-scrub-preview";
|
|
4050
|
+
let styleTag = document.getElementById(styleId);
|
|
4051
|
+
if (!styleTag) {
|
|
4052
|
+
styleTag = document.createElement("style");
|
|
4053
|
+
styleTag.id = styleId;
|
|
4054
|
+
applyNonce(styleTag);
|
|
4055
|
+
document.head.appendChild(styleTag);
|
|
4056
|
+
}
|
|
4057
|
+
const mediaExpr = media ?? (typeof maxWidth === "number" ? `(max-width: ${maxWidth}px)` : null);
|
|
4058
|
+
styleTag.textContent = mediaExpr ? `@media ${mediaExpr} { :root { ${name}: ${value}; } }` : `:root { ${name}: ${value}; }`;
|
|
4059
|
+
return;
|
|
4060
|
+
}
|
|
4061
|
+
if (event.data?.type === IFRAME_MESSAGE_TYPES.CSS_VARIABLE_SCOPED_CLEAR) {
|
|
4062
|
+
document.getElementById("meno-scrub-preview")?.remove();
|
|
3940
4063
|
return;
|
|
3941
4064
|
}
|
|
3942
4065
|
if (event.data?.type === IFRAME_MESSAGE_TYPES.INTERACTIVE_CSS_UPDATE) {
|
|
3943
4066
|
const css = event.data.css;
|
|
3944
4067
|
const styleId = "interactive-styles";
|
|
3945
|
-
|
|
3946
|
-
if (
|
|
3947
|
-
|
|
3948
|
-
|
|
3949
|
-
if (
|
|
3950
|
-
|
|
4068
|
+
if (!css) return;
|
|
4069
|
+
if (!document.head) return;
|
|
4070
|
+
const rewritten = rewriteViewportUnits(css);
|
|
4071
|
+
let styleTag = document.getElementById(styleId);
|
|
4072
|
+
if (!styleTag) {
|
|
4073
|
+
styleTag = document.createElement("style");
|
|
3951
4074
|
styleTag.id = styleId;
|
|
3952
|
-
styleTag
|
|
4075
|
+
applyNonce(styleTag);
|
|
3953
4076
|
document.head.appendChild(styleTag);
|
|
3954
4077
|
}
|
|
4078
|
+
styleTag.textContent = rewritten;
|
|
3955
4079
|
}
|
|
3956
4080
|
};
|
|
3957
4081
|
window.addEventListener("message", handleMessage);
|
|
3958
4082
|
return () => window.removeEventListener("message", handleMessage);
|
|
3959
4083
|
}, []);
|
|
4084
|
+
useEffect2(() => {
|
|
4085
|
+
if (typeof window === "undefined") return;
|
|
4086
|
+
const clearScrubPreview = () => {
|
|
4087
|
+
document.getElementById("meno-scrub-preview")?.remove();
|
|
4088
|
+
};
|
|
4089
|
+
document.addEventListener("hmr-variables-update", clearScrubPreview);
|
|
4090
|
+
return () => document.removeEventListener("hmr-variables-update", clearScrubPreview);
|
|
4091
|
+
}, []);
|
|
3960
4092
|
useEffect2(() => {
|
|
3961
4093
|
if (typeof window === "undefined") return;
|
|
3962
4094
|
const handleMessage = (event) => {
|
|
@@ -3969,6 +4101,7 @@ function Router(props = {}) {
|
|
|
3969
4101
|
setPreviewComponentTree(null);
|
|
3970
4102
|
} else if (event.data?.type === IFRAME_MESSAGE_TYPES.PAGE_DATA_COMMITTED) {
|
|
3971
4103
|
lastCommitTimestampRef.current = Date.now();
|
|
4104
|
+
lastCommitStructureChangedRef.current = event.data.structureChanged !== false;
|
|
3972
4105
|
const pageData = event.data.pageData;
|
|
3973
4106
|
if (pageData?.root) {
|
|
3974
4107
|
setComponentTree(pageData.root);
|
|
@@ -3977,6 +4110,7 @@ function Router(props = {}) {
|
|
|
3977
4110
|
}
|
|
3978
4111
|
} else if (event.data?.type === IFRAME_MESSAGE_TYPES.COMPONENT_DEFINITION_COMMITTED) {
|
|
3979
4112
|
lastCommitTimestampRef.current = Date.now();
|
|
4113
|
+
lastCommitStructureChangedRef.current = event.data.structureChanged !== false;
|
|
3980
4114
|
const { componentName, definition } = event.data;
|
|
3981
4115
|
if (componentName && definition) {
|
|
3982
4116
|
services.componentRegistry.register(componentName, definition);
|
|
@@ -4012,7 +4146,9 @@ function Router(props = {}) {
|
|
|
4012
4146
|
styles: registryData
|
|
4013
4147
|
}, "*");
|
|
4014
4148
|
}
|
|
4015
|
-
|
|
4149
|
+
const shouldRunScripts = !disableScripts && lastCommitStructureChangedRef.current;
|
|
4150
|
+
lastCommitStructureChangedRef.current = true;
|
|
4151
|
+
if (shouldRunScripts) {
|
|
4016
4152
|
const timeoutId = setTimeout(() => {
|
|
4017
4153
|
services.scriptExecutor.execute();
|
|
4018
4154
|
}, 100);
|
|
@@ -4429,6 +4565,7 @@ ${vars}
|
|
|
4429
4565
|
if (!themeStyleTag) {
|
|
4430
4566
|
themeStyleTag = document.createElement("style");
|
|
4431
4567
|
themeStyleTag.id = "hmr-theme-variables";
|
|
4568
|
+
applyNonce(themeStyleTag);
|
|
4432
4569
|
const mainStyle = document.querySelector("style");
|
|
4433
4570
|
if (mainStyle && mainStyle.nextSibling) {
|
|
4434
4571
|
document.head.insertBefore(themeStyleTag, mainStyle.nextSibling);
|
|
@@ -4646,6 +4783,159 @@ function mergeStyles(...styles) {
|
|
|
4646
4783
|
}, {});
|
|
4647
4784
|
}
|
|
4648
4785
|
|
|
4786
|
+
// lib/client/hmrCssReload.ts
|
|
4787
|
+
async function injectUpdatedThemeCSS2() {
|
|
4788
|
+
try {
|
|
4789
|
+
const themesResponse = await fetch("/api/themes");
|
|
4790
|
+
if (!themesResponse.ok) return;
|
|
4791
|
+
const themesData = await themesResponse.json();
|
|
4792
|
+
const themeColors = {};
|
|
4793
|
+
for (const theme of themesData.themes) {
|
|
4794
|
+
const colorResponse = await fetch(
|
|
4795
|
+
`/api/colors?theme=${encodeURIComponent(theme.name)}`
|
|
4796
|
+
);
|
|
4797
|
+
if (colorResponse.ok) {
|
|
4798
|
+
themeColors[theme.name] = (await colorResponse.json()).colors;
|
|
4799
|
+
}
|
|
4800
|
+
}
|
|
4801
|
+
const defaultResponse = await fetch("/api/colors");
|
|
4802
|
+
if (defaultResponse.ok) {
|
|
4803
|
+
themeColors["default"] = (await defaultResponse.json()).colors;
|
|
4804
|
+
}
|
|
4805
|
+
let css = "";
|
|
4806
|
+
if (themeColors["default"]) {
|
|
4807
|
+
const vars = Object.entries(themeColors["default"]).map(([name, value]) => ` --${name}: ${value};`).join("\n");
|
|
4808
|
+
css += `:root {
|
|
4809
|
+
${vars}
|
|
4810
|
+
}
|
|
4811
|
+
|
|
4812
|
+
`;
|
|
4813
|
+
}
|
|
4814
|
+
for (const theme of themesData.themes) {
|
|
4815
|
+
if (themeColors[theme.name]) {
|
|
4816
|
+
const vars = Object.entries(themeColors[theme.name]).map(([name, value]) => ` --${name}: ${value};`).join("\n");
|
|
4817
|
+
css += `[theme="${theme.name}"] {
|
|
4818
|
+
${vars}
|
|
4819
|
+
}
|
|
4820
|
+
|
|
4821
|
+
`;
|
|
4822
|
+
}
|
|
4823
|
+
}
|
|
4824
|
+
let styleTag = document.getElementById("hmr-theme-variables");
|
|
4825
|
+
if (!styleTag) {
|
|
4826
|
+
styleTag = document.createElement("style");
|
|
4827
|
+
styleTag.id = "hmr-theme-variables";
|
|
4828
|
+
applyNonce(styleTag);
|
|
4829
|
+
document.head.appendChild(styleTag);
|
|
4830
|
+
}
|
|
4831
|
+
styleTag.textContent = css;
|
|
4832
|
+
} catch {
|
|
4833
|
+
}
|
|
4834
|
+
}
|
|
4835
|
+
async function injectUpdatedVariablesCSS() {
|
|
4836
|
+
try {
|
|
4837
|
+
const response = await fetch("/api/variables-css");
|
|
4838
|
+
if (!response.ok) return;
|
|
4839
|
+
const css = await response.text();
|
|
4840
|
+
let styleTag = document.getElementById("hmr-css-variables");
|
|
4841
|
+
if (!styleTag) {
|
|
4842
|
+
styleTag = document.createElement("style");
|
|
4843
|
+
styleTag.id = "hmr-css-variables";
|
|
4844
|
+
applyNonce(styleTag);
|
|
4845
|
+
document.head.appendChild(styleTag);
|
|
4846
|
+
}
|
|
4847
|
+
styleTag.textContent = css;
|
|
4848
|
+
} catch {
|
|
4849
|
+
}
|
|
4850
|
+
}
|
|
4851
|
+
async function injectUpdatedFontsCSS() {
|
|
4852
|
+
try {
|
|
4853
|
+
const response = await fetch("/api/fonts-css");
|
|
4854
|
+
if (!response.ok) return;
|
|
4855
|
+
const css = await response.text();
|
|
4856
|
+
let styleTag = document.getElementById("hmr-fonts-css");
|
|
4857
|
+
if (!styleTag) {
|
|
4858
|
+
styleTag = document.createElement("style");
|
|
4859
|
+
styleTag.id = "hmr-fonts-css";
|
|
4860
|
+
applyNonce(styleTag);
|
|
4861
|
+
document.head.appendChild(styleTag);
|
|
4862
|
+
}
|
|
4863
|
+
styleTag.textContent = css;
|
|
4864
|
+
} catch {
|
|
4865
|
+
}
|
|
4866
|
+
}
|
|
4867
|
+
function setupCssHmrListeners() {
|
|
4868
|
+
if (typeof window === "undefined") return;
|
|
4869
|
+
if (!window.__hmrColorsInitialized) {
|
|
4870
|
+
window.__hmrColorsInitialized = true;
|
|
4871
|
+
document.addEventListener("hmr-colors-update", () => {
|
|
4872
|
+
void injectUpdatedThemeCSS2();
|
|
4873
|
+
});
|
|
4874
|
+
}
|
|
4875
|
+
if (!window.__hmrVariablesCSSInitialized) {
|
|
4876
|
+
window.__hmrVariablesCSSInitialized = true;
|
|
4877
|
+
document.addEventListener("hmr-variables-update", () => {
|
|
4878
|
+
void injectUpdatedVariablesCSS();
|
|
4879
|
+
});
|
|
4880
|
+
}
|
|
4881
|
+
if (!window.__hmrFontsCSSInitialized) {
|
|
4882
|
+
window.__hmrFontsCSSInitialized = true;
|
|
4883
|
+
document.addEventListener("hmr-fonts-update", () => {
|
|
4884
|
+
void injectUpdatedFontsCSS();
|
|
4885
|
+
});
|
|
4886
|
+
}
|
|
4887
|
+
if (!window.__hmrLibrariesInitialized) {
|
|
4888
|
+
window.__hmrLibrariesInitialized = true;
|
|
4889
|
+
document.addEventListener("hmr-libraries-update", () => {
|
|
4890
|
+
location.reload();
|
|
4891
|
+
});
|
|
4892
|
+
}
|
|
4893
|
+
}
|
|
4894
|
+
|
|
4895
|
+
// lib/client/fontFamiliesService.ts
|
|
4896
|
+
function extractFamilyFromPath(path) {
|
|
4897
|
+
const filename = path.split("/").pop() || "Font";
|
|
4898
|
+
const name = filename.replace(/\.(ttf|woff2?|otf)$/i, "");
|
|
4899
|
+
return name.split("-").map((part) => part.charAt(0).toUpperCase() + part.slice(1)).join(" ");
|
|
4900
|
+
}
|
|
4901
|
+
function extractFamilies(fonts) {
|
|
4902
|
+
if (!Array.isArray(fonts)) return [];
|
|
4903
|
+
const set = /* @__PURE__ */ new Set();
|
|
4904
|
+
for (const font of fonts) {
|
|
4905
|
+
const path = font.path || font.src;
|
|
4906
|
+
const family = font.family || (path ? extractFamilyFromPath(path) : null);
|
|
4907
|
+
if (family) set.add(family);
|
|
4908
|
+
}
|
|
4909
|
+
return [...set];
|
|
4910
|
+
}
|
|
4911
|
+
var cachedFamilies = null;
|
|
4912
|
+
var inFlight = null;
|
|
4913
|
+
async function fetchFontFamilies() {
|
|
4914
|
+
if (cachedFamilies) return cachedFamilies;
|
|
4915
|
+
if (inFlight) return inFlight;
|
|
4916
|
+
inFlight = fetch("/api/config").then((res) => res.ok ? res.json() : { fonts: [] }).then((config) => {
|
|
4917
|
+
cachedFamilies = extractFamilies(config.fonts);
|
|
4918
|
+
return cachedFamilies;
|
|
4919
|
+
}).catch(() => {
|
|
4920
|
+
cachedFamilies = [];
|
|
4921
|
+
return cachedFamilies;
|
|
4922
|
+
}).finally(() => {
|
|
4923
|
+
inFlight = null;
|
|
4924
|
+
});
|
|
4925
|
+
return inFlight;
|
|
4926
|
+
}
|
|
4927
|
+
function getCachedFontFamilies() {
|
|
4928
|
+
return cachedFamilies || [];
|
|
4929
|
+
}
|
|
4930
|
+
function invalidateFontFamilies() {
|
|
4931
|
+
cachedFamilies = null;
|
|
4932
|
+
inFlight = null;
|
|
4933
|
+
}
|
|
4934
|
+
async function initializeFontFamilies(forceRefresh = false) {
|
|
4935
|
+
if (forceRefresh) invalidateFontFamilies();
|
|
4936
|
+
await fetchFontFamilies();
|
|
4937
|
+
}
|
|
4938
|
+
|
|
4649
4939
|
// lib/client/hooks/usePropertyAutocomplete.ts
|
|
4650
4940
|
import { useState as useState5, useRef as useRef4 } from "react";
|
|
4651
4941
|
function usePropertyAutocomplete(initialProperty = "") {
|
|
@@ -4775,8 +5065,10 @@ export {
|
|
|
4775
5065
|
detectSSRContent,
|
|
4776
5066
|
elementRegistry,
|
|
4777
5067
|
evaluateTemplate,
|
|
5068
|
+
fetchFontFamilies,
|
|
4778
5069
|
fetchI18nConfig,
|
|
4779
5070
|
getCachedBreakpointConfig,
|
|
5071
|
+
getCachedFontFamilies,
|
|
4780
5072
|
getCachedRemConversionConfig,
|
|
4781
5073
|
getCachedResponsiveScalesConfig,
|
|
4782
5074
|
getColorVariableSuggestions,
|
|
@@ -4789,6 +5081,8 @@ export {
|
|
|
4789
5081
|
hasTemplates,
|
|
4790
5082
|
initializeBreakpoints,
|
|
4791
5083
|
initializeConfig,
|
|
5084
|
+
initializeFontFamilies,
|
|
5085
|
+
invalidateFontFamilies,
|
|
4792
5086
|
invalidateI18nConfig,
|
|
4793
5087
|
isColorVariableValue,
|
|
4794
5088
|
isHtmlMapping,
|
|
@@ -4811,6 +5105,7 @@ export {
|
|
|
4811
5105
|
resolveStyleMapping,
|
|
4812
5106
|
setElementRegistry,
|
|
4813
5107
|
setI18nConfig,
|
|
5108
|
+
setupCssHmrListeners,
|
|
4814
5109
|
useColorVariables,
|
|
4815
5110
|
usePropertyAutocomplete,
|
|
4816
5111
|
useTheme,
|