streetui 1.8.0 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/bin.cjs +1 -1
- package/dist/bin.cjs.map +1 -1
- package/dist/bin.js +1 -1
- package/dist/bin.js.map +1 -1
- package/dist/create-bin.cjs +1 -1
- package/dist/create-bin.cjs.map +1 -1
- package/dist/create-bin.js +1 -1
- package/dist/create-bin.js.map +1 -1
- package/dist/{compile-CJJQYi71.d.cts → hydration-diagnostics-CFYDXBlm.d.cts} +471 -5
- package/dist/{compile-CJJQYi71.d.ts → hydration-diagnostics-CFYDXBlm.d.ts} +471 -5
- package/dist/index.cjs +1401 -47
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +598 -147
- package/dist/index.d.ts +598 -147
- package/dist/index.js +1379 -47
- package/dist/index.js.map +1 -1
- package/dist/renderer-interface-BUhHV7ja.d.cts +26 -0
- package/dist/renderer-interface-B_-hWnKk.d.ts +26 -0
- package/dist/{server-CnLEnlYU.d.cts → server-C0PvFBzD.d.ts} +181 -2
- package/dist/{server-DNlg7ou2.d.ts → server-DnAOFpMP.d.cts} +181 -2
- package/dist/server.cjs +482 -32
- package/dist/server.cjs.map +1 -1
- package/dist/server.d.cts +2 -2
- package/dist/server.d.ts +2 -2
- package/dist/server.js +481 -32
- package/dist/server.js.map +1 -1
- package/dist/testing.cjs +754 -41
- package/dist/testing.cjs.map +1 -1
- package/dist/testing.d.cts +42 -4
- package/dist/testing.d.ts +42 -4
- package/dist/testing.js +746 -40
- package/dist/testing.js.map +1 -1
- package/package.json +1 -1
- package/dist/hydration-diagnostics-BQeehq3i.d.cts +0 -89
- package/dist/hydration-diagnostics-DNAJumYF.d.ts +0 -89
package/dist/index.cjs
CHANGED
|
@@ -37,6 +37,8 @@ __export(src_exports, {
|
|
|
37
37
|
FOCUSABLE_SELECTOR: () => FOCUSABLE_SELECTOR,
|
|
38
38
|
FormBuilderImpl: () => FormBuilderImpl,
|
|
39
39
|
GraphNode: () => GraphNode,
|
|
40
|
+
HeadManager: () => HeadManager,
|
|
41
|
+
HttpError: () => HttpError,
|
|
40
42
|
Lifecycle: () => Lifecycle,
|
|
41
43
|
ListBuilderImpl: () => ListBuilderImpl,
|
|
42
44
|
NodeInstance: () => NodeInstance,
|
|
@@ -60,6 +62,7 @@ __export(src_exports, {
|
|
|
60
62
|
StreetFrameworkError: () => StreetFrameworkError,
|
|
61
63
|
StreetRenderHandle: () => StreetRenderHandle,
|
|
62
64
|
StreetRendererImpl: () => StreetRendererImpl,
|
|
65
|
+
TransitionController: () => TransitionController,
|
|
63
66
|
VERSION: () => VERSION,
|
|
64
67
|
a11yIds: () => a11yIds,
|
|
65
68
|
applyNodeProps: () => applyNodeProps,
|
|
@@ -74,8 +77,11 @@ __export(src_exports, {
|
|
|
74
77
|
consoleDiagnosticSink: () => consoleDiagnosticSink,
|
|
75
78
|
consoleHydrationDiagnosticSink: () => consoleHydrationDiagnosticSink,
|
|
76
79
|
containFocus: () => containFocus,
|
|
80
|
+
createAnnouncer: () => createAnnouncer,
|
|
77
81
|
createApplication: () => createApplication,
|
|
82
|
+
createAuthSession: () => createAuthSession,
|
|
78
83
|
createBrowserHistory: () => createBrowserHistory,
|
|
84
|
+
createClient: () => createClient,
|
|
79
85
|
createContext: () => createContext,
|
|
80
86
|
createDevTools: () => createDevTools,
|
|
81
87
|
createForm: () => createForm,
|
|
@@ -91,10 +97,12 @@ __export(src_exports, {
|
|
|
91
97
|
createStreetEvent: () => createStreetEvent,
|
|
92
98
|
defineConfig: () => defineConfig,
|
|
93
99
|
derived: () => derived,
|
|
100
|
+
describeError: () => describeError,
|
|
94
101
|
diagnosePerformance: () => diagnosePerformance,
|
|
95
102
|
effect: () => effect,
|
|
96
103
|
email: () => email,
|
|
97
104
|
environment: () => environment,
|
|
105
|
+
escapeHtml: () => escapeHtml,
|
|
98
106
|
escapeHtmlAttr: () => escapeHtmlAttr,
|
|
99
107
|
escapeHtmlText: () => escapeHtmlText,
|
|
100
108
|
flushSync: () => flushSync,
|
|
@@ -108,6 +116,7 @@ __export(src_exports, {
|
|
|
108
116
|
generateApplicationId: () => generateApplicationId,
|
|
109
117
|
generateNodeId: () => generateNodeId,
|
|
110
118
|
getFocusable: () => getFocusable,
|
|
119
|
+
getResolvedTransition: () => getResolvedTransition,
|
|
111
120
|
globalEventBus: () => globalEventBus,
|
|
112
121
|
headingUpdate: () => headingUpdate,
|
|
113
122
|
hydrateGraph: () => hydrateGraph,
|
|
@@ -118,12 +127,16 @@ __export(src_exports, {
|
|
|
118
127
|
inspectForm: () => inspectForm,
|
|
119
128
|
inspectGraph: () => inspectGraph,
|
|
120
129
|
inspectI18n: () => inspectI18n,
|
|
130
|
+
inspectInteractions: () => inspectInteractions,
|
|
121
131
|
inspectResource: () => inspectResource,
|
|
122
132
|
inspectRouter: () => inspectRouter,
|
|
123
133
|
inspectSignal: () => inspectSignal,
|
|
124
134
|
interpolate: () => interpolate,
|
|
125
135
|
isBatching: () => isBatching,
|
|
126
136
|
isComponentDefinition: () => isComponentDefinition,
|
|
137
|
+
isHeadContribution: () => isHeadContribution,
|
|
138
|
+
isTransitionConfig: () => isTransitionConfig,
|
|
139
|
+
linkUpdate: () => linkUpdate,
|
|
127
140
|
matchPattern: () => matchPattern,
|
|
128
141
|
matchRoutes: () => matchRoutes,
|
|
129
142
|
maxLength: () => maxLength,
|
|
@@ -131,6 +144,7 @@ __export(src_exports, {
|
|
|
131
144
|
mountGraph: () => mountGraph,
|
|
132
145
|
mountNode: () => mountNode,
|
|
133
146
|
mountRouter: () => mountRouter,
|
|
147
|
+
mutation: () => mutation,
|
|
134
148
|
nextId: () => nextId,
|
|
135
149
|
nodeIdPrefix: () => nodeIdPrefix,
|
|
136
150
|
nodeTypeStats: () => nodeTypeStats,
|
|
@@ -147,14 +161,21 @@ __export(src_exports, {
|
|
|
147
161
|
readState: () => readState,
|
|
148
162
|
reconcileChildren: () => reconcileChildren,
|
|
149
163
|
reconcileChildrenByPlan: () => reconcileChildrenByPlan,
|
|
164
|
+
renderDevToolsHTML: () => renderDevToolsHTML,
|
|
165
|
+
renderHead: () => renderHead,
|
|
150
166
|
renderToString: () => renderToString,
|
|
151
167
|
reportDiagnostic: () => reportDiagnostic,
|
|
168
|
+
reportError: () => reportError,
|
|
152
169
|
required: () => required,
|
|
153
170
|
resetIdCounter: () => resetIdCounter,
|
|
171
|
+
resolveHead: () => resolveHead,
|
|
154
172
|
resolveTag: () => resolveTag,
|
|
173
|
+
resolveTransition: () => resolveTransition,
|
|
155
174
|
resource: () => resource,
|
|
156
175
|
restoreFocus: () => restoreFocus,
|
|
157
176
|
routerOutlet: () => routerOutlet,
|
|
177
|
+
rovingMenu: () => rovingMenu,
|
|
178
|
+
runElementTransition: () => runElementTransition,
|
|
158
179
|
runValidators: () => runValidators,
|
|
159
180
|
saveFocus: () => saveFocus,
|
|
160
181
|
scheduleImmediate: () => scheduleImmediate,
|
|
@@ -175,6 +196,7 @@ __export(src_exports, {
|
|
|
175
196
|
validateGraph: () => validateGraph,
|
|
176
197
|
wireComponentBehavior: () => wireComponentBehavior,
|
|
177
198
|
wireEvents: () => wireEvents,
|
|
199
|
+
wireHeadBehavior: () => wireHeadBehavior,
|
|
178
200
|
wireOverlayBehavior: () => wireOverlayBehavior,
|
|
179
201
|
wireReactiveList: () => wireReactiveList,
|
|
180
202
|
wireSignalBindings: () => wireSignalBindings
|
|
@@ -182,7 +204,7 @@ __export(src_exports, {
|
|
|
182
204
|
module.exports = __toCommonJS(src_exports);
|
|
183
205
|
|
|
184
206
|
// src/version.ts
|
|
185
|
-
var VERSION = "
|
|
207
|
+
var VERSION = "2.0.0";
|
|
186
208
|
|
|
187
209
|
// ../state/src/signal.ts
|
|
188
210
|
var _activeConsumer = null;
|
|
@@ -522,6 +544,198 @@ function resource(loader, options = {}) {
|
|
|
522
544
|
};
|
|
523
545
|
}
|
|
524
546
|
|
|
547
|
+
// ../state/src/mutation.ts
|
|
548
|
+
function mutation(mutator, options = {}) {
|
|
549
|
+
const status = signal("idle");
|
|
550
|
+
const data = signal(void 0);
|
|
551
|
+
const error = signal(void 0);
|
|
552
|
+
const pending = derived(() => status.get() === "loading");
|
|
553
|
+
let disposed = false;
|
|
554
|
+
let runId = 0;
|
|
555
|
+
const mutate = async (args) => {
|
|
556
|
+
if (disposed) {
|
|
557
|
+
return await mutator(args);
|
|
558
|
+
}
|
|
559
|
+
const myRun = ++runId;
|
|
560
|
+
batch(() => {
|
|
561
|
+
error.set(void 0);
|
|
562
|
+
status.set("loading");
|
|
563
|
+
});
|
|
564
|
+
try {
|
|
565
|
+
const result = await mutator(args);
|
|
566
|
+
if (!disposed && myRun === runId) {
|
|
567
|
+
batch(() => {
|
|
568
|
+
data.set(result);
|
|
569
|
+
error.set(void 0);
|
|
570
|
+
status.set("success");
|
|
571
|
+
});
|
|
572
|
+
}
|
|
573
|
+
if (!disposed && myRun === runId) {
|
|
574
|
+
await options.onSuccess?.(result, args);
|
|
575
|
+
await options.onSettled?.(args);
|
|
576
|
+
}
|
|
577
|
+
return result;
|
|
578
|
+
} catch (err) {
|
|
579
|
+
if (!disposed && myRun === runId) {
|
|
580
|
+
batch(() => {
|
|
581
|
+
error.set(err);
|
|
582
|
+
status.set("error");
|
|
583
|
+
});
|
|
584
|
+
await options.onError?.(err, args);
|
|
585
|
+
await options.onSettled?.(args);
|
|
586
|
+
}
|
|
587
|
+
throw err;
|
|
588
|
+
}
|
|
589
|
+
};
|
|
590
|
+
const reset = () => {
|
|
591
|
+
batch(() => {
|
|
592
|
+
status.set("idle");
|
|
593
|
+
data.set(void 0);
|
|
594
|
+
error.set(void 0);
|
|
595
|
+
});
|
|
596
|
+
};
|
|
597
|
+
const dispose = () => {
|
|
598
|
+
disposed = true;
|
|
599
|
+
};
|
|
600
|
+
if (options.onCleanup !== void 0) options.onCleanup(dispose);
|
|
601
|
+
return { status, data, error, pending, mutate, reset, dispose };
|
|
602
|
+
}
|
|
603
|
+
|
|
604
|
+
// ../state/src/client.ts
|
|
605
|
+
var HttpError = class extends Error {
|
|
606
|
+
status;
|
|
607
|
+
statusText;
|
|
608
|
+
url;
|
|
609
|
+
body;
|
|
610
|
+
constructor(status, statusText, url, body) {
|
|
611
|
+
super(`HTTP ${status} ${statusText} for ${url}`);
|
|
612
|
+
this.name = "HttpError";
|
|
613
|
+
this.status = status;
|
|
614
|
+
this.statusText = statusText;
|
|
615
|
+
this.url = url;
|
|
616
|
+
this.body = body;
|
|
617
|
+
}
|
|
618
|
+
};
|
|
619
|
+
function joinUrl(baseUrl, path) {
|
|
620
|
+
if (baseUrl === void 0 || baseUrl === "") return path;
|
|
621
|
+
const b = baseUrl.endsWith("/") ? baseUrl.slice(0, -1) : baseUrl;
|
|
622
|
+
const p = path.startsWith("/") ? path : `/${path}`;
|
|
623
|
+
return `${b}${p}`;
|
|
624
|
+
}
|
|
625
|
+
function withQuery(url, query) {
|
|
626
|
+
if (query === void 0) return url;
|
|
627
|
+
const params = new URLSearchParams();
|
|
628
|
+
for (const [k, v] of Object.entries(query)) params.set(k, String(v));
|
|
629
|
+
const qs = params.toString();
|
|
630
|
+
if (qs === "") return url;
|
|
631
|
+
return url.includes("?") ? `${url}&${qs}` : `${url}?${qs}`;
|
|
632
|
+
}
|
|
633
|
+
function createClient(config = {}) {
|
|
634
|
+
const doFetch = config.fetch ?? ((input, init) => {
|
|
635
|
+
if (typeof fetch === "undefined") {
|
|
636
|
+
throw new Error("createClient: no global fetch; pass { fetch } explicitly");
|
|
637
|
+
}
|
|
638
|
+
return fetch(input, init);
|
|
639
|
+
});
|
|
640
|
+
async function request(method, path, body, reqConfig = {}) {
|
|
641
|
+
const url = withQuery(joinUrl(config.baseUrl, path), reqConfig.query);
|
|
642
|
+
const headers = { ...config.headers, ...reqConfig.headers };
|
|
643
|
+
const init = { method, headers };
|
|
644
|
+
if (reqConfig.signal !== void 0) init.signal = reqConfig.signal;
|
|
645
|
+
if (body !== void 0) {
|
|
646
|
+
if (headers["Content-Type"] === void 0) headers["Content-Type"] = "application/json";
|
|
647
|
+
init.body = JSON.stringify(body);
|
|
648
|
+
}
|
|
649
|
+
const response = await doFetch(url, init);
|
|
650
|
+
const parsed = await parseBody(response);
|
|
651
|
+
if (!response.ok) {
|
|
652
|
+
throw new HttpError(response.status, response.statusText, url, parsed);
|
|
653
|
+
}
|
|
654
|
+
return parsed;
|
|
655
|
+
}
|
|
656
|
+
return {
|
|
657
|
+
request,
|
|
658
|
+
get: (path, c) => request("GET", path, void 0, c),
|
|
659
|
+
post: (path, b, c) => request("POST", path, b, c),
|
|
660
|
+
put: (path, b, c) => request("PUT", path, b, c),
|
|
661
|
+
patch: (path, b, c) => request("PATCH", path, b, c),
|
|
662
|
+
del: (path, c) => request("DELETE", path, void 0, c),
|
|
663
|
+
resource: (path, options = {}) => {
|
|
664
|
+
const { query, ...resourceOptions } = options;
|
|
665
|
+
return resource(
|
|
666
|
+
(ctx) => request("GET", path, void 0, { signal: ctx.signal, ...query !== void 0 ? { query } : {} }),
|
|
667
|
+
resourceOptions
|
|
668
|
+
);
|
|
669
|
+
},
|
|
670
|
+
mutation: (method, path, options) => mutation((args) => request(method, path, args), options ?? {})
|
|
671
|
+
};
|
|
672
|
+
}
|
|
673
|
+
async function parseBody(response) {
|
|
674
|
+
const text = await response.text();
|
|
675
|
+
if (text === "") return void 0;
|
|
676
|
+
const type = response.headers.get("content-type") ?? "";
|
|
677
|
+
if (type.includes("application/json")) {
|
|
678
|
+
try {
|
|
679
|
+
return JSON.parse(text);
|
|
680
|
+
} catch {
|
|
681
|
+
return text;
|
|
682
|
+
}
|
|
683
|
+
}
|
|
684
|
+
return text;
|
|
685
|
+
}
|
|
686
|
+
|
|
687
|
+
// ../state/src/auth.ts
|
|
688
|
+
function createAuthSession(config) {
|
|
689
|
+
const session = resource(
|
|
690
|
+
(ctx) => config.loadUser(ctx),
|
|
691
|
+
{
|
|
692
|
+
...config.immediate !== void 0 ? { immediate: config.immediate } : {},
|
|
693
|
+
...config.onCleanup !== void 0 ? { onCleanup: config.onCleanup } : {}
|
|
694
|
+
}
|
|
695
|
+
);
|
|
696
|
+
const status = derived(() => {
|
|
697
|
+
const s = session.status.get();
|
|
698
|
+
const d = session.data.get();
|
|
699
|
+
if (s === "error") return "error";
|
|
700
|
+
if (s === "idle" || s === "loading" && d === void 0) return "loading";
|
|
701
|
+
return d === null || d === void 0 ? "unauthenticated" : "authenticated";
|
|
702
|
+
});
|
|
703
|
+
const user = derived(() => {
|
|
704
|
+
const d = session.data.get();
|
|
705
|
+
return d === null ? void 0 : d;
|
|
706
|
+
});
|
|
707
|
+
const authenticated = derived(() => status.get() === "authenticated");
|
|
708
|
+
const unauthenticated = derived(() => status.get() === "unauthenticated");
|
|
709
|
+
const loading = derived(() => status.get() === "loading");
|
|
710
|
+
const logoutMutation = mutation(
|
|
711
|
+
async () => {
|
|
712
|
+
await config.logout?.();
|
|
713
|
+
},
|
|
714
|
+
{ onSuccess: () => session.refetch() }
|
|
715
|
+
);
|
|
716
|
+
const dispose = () => {
|
|
717
|
+
session.dispose();
|
|
718
|
+
status.dispose();
|
|
719
|
+
user.dispose();
|
|
720
|
+
authenticated.dispose();
|
|
721
|
+
unauthenticated.dispose();
|
|
722
|
+
loading.dispose();
|
|
723
|
+
logoutMutation.dispose();
|
|
724
|
+
};
|
|
725
|
+
return {
|
|
726
|
+
status,
|
|
727
|
+
user,
|
|
728
|
+
error: session.error,
|
|
729
|
+
authenticated,
|
|
730
|
+
unauthenticated,
|
|
731
|
+
loading,
|
|
732
|
+
loggingOut: logoutMutation.pending,
|
|
733
|
+
refresh: () => session.refetch(),
|
|
734
|
+
logout: () => logoutMutation.mutate(void 0),
|
|
735
|
+
dispose
|
|
736
|
+
};
|
|
737
|
+
}
|
|
738
|
+
|
|
525
739
|
// ../core/src/a11y-ids.ts
|
|
526
740
|
var UNSAFE = /[^A-Za-z0-9_-]+/g;
|
|
527
741
|
function toIdToken(base) {
|
|
@@ -537,6 +751,9 @@ function a11yIds(base) {
|
|
|
537
751
|
description: `${token}-description`,
|
|
538
752
|
error: `${token}-error`,
|
|
539
753
|
title: `${token}-title`,
|
|
754
|
+
trigger: `${token}-trigger`,
|
|
755
|
+
controls: `${token}-controls`,
|
|
756
|
+
owns: `${token}-owns`,
|
|
540
757
|
id: (suffix) => `${token}-${toIdToken(suffix)}`
|
|
541
758
|
};
|
|
542
759
|
}
|
|
@@ -785,9 +1002,13 @@ function formatDiagnosticContext(context) {
|
|
|
785
1002
|
const parts = [];
|
|
786
1003
|
if (context.package !== void 0) parts.push(`package=${context.package}`);
|
|
787
1004
|
if (context.operation !== void 0) parts.push(`operation=${context.operation}`);
|
|
1005
|
+
if (context.component !== void 0) parts.push(`component=${context.component}`);
|
|
1006
|
+
if (context.phase !== void 0) parts.push(`phase=${context.phase}`);
|
|
788
1007
|
if (context.nodeId !== void 0) parts.push(`node=${context.nodeId}`);
|
|
1008
|
+
if (context.element !== void 0) parts.push(`element=${context.element}`);
|
|
789
1009
|
if (context.route !== void 0) parts.push(`route=${context.route}`);
|
|
790
1010
|
if (context.resource !== void 0) parts.push(`resource=${context.resource}`);
|
|
1011
|
+
if (context.signal !== void 0) parts.push(`signal=${context.signal}`);
|
|
791
1012
|
return parts.length > 0 ? ` [${parts.join(", ")}]` : "";
|
|
792
1013
|
}
|
|
793
1014
|
var StreetFrameworkError = class extends Error {
|
|
@@ -818,6 +1039,42 @@ function consoleDiagnosticSink(logger = console) {
|
|
|
818
1039
|
error: (m, c) => logger.error?.(`${m}${formatDiagnosticContext(c)}`)
|
|
819
1040
|
};
|
|
820
1041
|
}
|
|
1042
|
+
function describeErrorAt(error, context, options, depth) {
|
|
1043
|
+
const isError = error instanceof Error;
|
|
1044
|
+
const name = isError ? error.name : "Error";
|
|
1045
|
+
const message = isError ? error.message : safeStringify(error);
|
|
1046
|
+
const report = { name, message, isError };
|
|
1047
|
+
if (context !== void 0) report.context = context;
|
|
1048
|
+
if (options.includeStack === true && isError && typeof error.stack === "string") {
|
|
1049
|
+
report.stack = error.stack;
|
|
1050
|
+
}
|
|
1051
|
+
if (options.includeCause === true && isError && depth < 4) {
|
|
1052
|
+
const cause = error.cause;
|
|
1053
|
+
if (cause !== void 0 && cause !== null) {
|
|
1054
|
+
report.cause = describeErrorAt(cause, void 0, options, depth + 1);
|
|
1055
|
+
}
|
|
1056
|
+
}
|
|
1057
|
+
return report;
|
|
1058
|
+
}
|
|
1059
|
+
function safeStringify(value) {
|
|
1060
|
+
if (typeof value === "string") return value;
|
|
1061
|
+
if (value === null) return "null";
|
|
1062
|
+
if (value === void 0) return "undefined";
|
|
1063
|
+
const t = typeof value;
|
|
1064
|
+
if (t === "number" || t === "boolean" || t === "bigint" || t === "symbol") {
|
|
1065
|
+
return String(value);
|
|
1066
|
+
}
|
|
1067
|
+
const ctor = t === "object" && value !== null ? value.constructor?.name ?? "Object" : t;
|
|
1068
|
+
return `[non-Error ${ctor}]`;
|
|
1069
|
+
}
|
|
1070
|
+
function describeError(error, context, options = {}) {
|
|
1071
|
+
return describeErrorAt(error, context, options, 0);
|
|
1072
|
+
}
|
|
1073
|
+
function reportError(sink, error, context, options = {}) {
|
|
1074
|
+
const report = describeError(error, context, options);
|
|
1075
|
+
reportDiagnostic(sink, "error", report.message, report.context);
|
|
1076
|
+
return report;
|
|
1077
|
+
}
|
|
821
1078
|
|
|
822
1079
|
// ../graph/src/graph-node.ts
|
|
823
1080
|
var GraphNode = class _GraphNode {
|
|
@@ -987,6 +1244,8 @@ var ApplicationGraph = class {
|
|
|
987
1244
|
this.handlers.delete(`__listplan__${node.id}`);
|
|
988
1245
|
this.handlers.delete(`__overlay__${node.id}`);
|
|
989
1246
|
this.handlers.delete(`__component__${node.id}`);
|
|
1247
|
+
this.handlers.delete(`__transition__${node.id}`);
|
|
1248
|
+
this.handlers.delete(`__head__${node.id}`);
|
|
990
1249
|
}
|
|
991
1250
|
// ── Handler registry ──────────────────────────────────────────────────────
|
|
992
1251
|
registerHandler(key, fn) {
|
|
@@ -1075,6 +1334,162 @@ var ApplicationGraph = class {
|
|
|
1075
1334
|
}
|
|
1076
1335
|
};
|
|
1077
1336
|
|
|
1337
|
+
// ../dsl/src/transition.ts
|
|
1338
|
+
function classes(value) {
|
|
1339
|
+
if (value === void 0) return [];
|
|
1340
|
+
const out = [];
|
|
1341
|
+
for (const token of value.split(/\s+/)) {
|
|
1342
|
+
if (token.length > 0 && !out.includes(token)) out.push(token);
|
|
1343
|
+
}
|
|
1344
|
+
return out;
|
|
1345
|
+
}
|
|
1346
|
+
function merge(a, b) {
|
|
1347
|
+
const out = [...a];
|
|
1348
|
+
for (const token of b) if (!out.includes(token)) out.push(token);
|
|
1349
|
+
return out;
|
|
1350
|
+
}
|
|
1351
|
+
function resolveTransition(config) {
|
|
1352
|
+
const n = config.name;
|
|
1353
|
+
const enterActive = merge(
|
|
1354
|
+
classes(config.enter),
|
|
1355
|
+
classes(config.enterActive ?? (n !== void 0 ? `${n}-enter-active` : void 0))
|
|
1356
|
+
);
|
|
1357
|
+
const leaveActive = merge(
|
|
1358
|
+
classes(config.leave),
|
|
1359
|
+
classes(config.leaveActive ?? (n !== void 0 ? `${n}-leave-active` : void 0))
|
|
1360
|
+
);
|
|
1361
|
+
return {
|
|
1362
|
+
enterActive,
|
|
1363
|
+
enterFrom: classes(config.enterFrom ?? (n !== void 0 ? `${n}-enter-from` : void 0)),
|
|
1364
|
+
enterTo: classes(config.enterTo ?? (n !== void 0 ? `${n}-enter-to` : void 0)),
|
|
1365
|
+
leaveActive,
|
|
1366
|
+
leaveFrom: classes(config.leaveFrom ?? (n !== void 0 ? `${n}-leave-from` : void 0)),
|
|
1367
|
+
leaveTo: classes(config.leaveTo ?? (n !== void 0 ? `${n}-leave-to` : void 0)),
|
|
1368
|
+
appear: config.appear ?? false,
|
|
1369
|
+
duration: config.duration ?? 1e3
|
|
1370
|
+
};
|
|
1371
|
+
}
|
|
1372
|
+
function isTransitionConfig(value) {
|
|
1373
|
+
if (value === null || typeof value !== "object") return false;
|
|
1374
|
+
const o = value;
|
|
1375
|
+
return typeof o["name"] === "string" || typeof o["enter"] === "string" || typeof o["enterActive"] === "string" || typeof o["enterFrom"] === "string" || typeof o["leave"] === "string" || typeof o["leaveActive"] === "string" || typeof o["leaveFrom"] === "string";
|
|
1376
|
+
}
|
|
1377
|
+
|
|
1378
|
+
// ../dsl/src/head.ts
|
|
1379
|
+
function metaDedupKey(m) {
|
|
1380
|
+
if (m.charset !== void 0) return "meta:charset";
|
|
1381
|
+
if (m.name !== void 0) return `meta:name=${m.name}`;
|
|
1382
|
+
if (m.property !== void 0) return `meta:property=${m.property}`;
|
|
1383
|
+
if (m.httpEquiv !== void 0) return `meta:http-equiv=${m.httpEquiv}`;
|
|
1384
|
+
return void 0;
|
|
1385
|
+
}
|
|
1386
|
+
function metaAttrs(m) {
|
|
1387
|
+
const attrs = {};
|
|
1388
|
+
if (m.charset !== void 0) attrs["charset"] = m.charset;
|
|
1389
|
+
if (m.name !== void 0) attrs["name"] = m.name;
|
|
1390
|
+
if (m.property !== void 0) attrs["property"] = m.property;
|
|
1391
|
+
if (m.httpEquiv !== void 0) attrs["http-equiv"] = m.httpEquiv;
|
|
1392
|
+
if (m.content !== void 0) attrs["content"] = m.content;
|
|
1393
|
+
return attrs;
|
|
1394
|
+
}
|
|
1395
|
+
function linkAttrs(l) {
|
|
1396
|
+
const attrs = { rel: l.rel, href: l.href };
|
|
1397
|
+
if (l.sizes !== void 0) attrs["sizes"] = l.sizes;
|
|
1398
|
+
if (l.type !== void 0) attrs["type"] = l.type;
|
|
1399
|
+
if (l.media !== void 0) attrs["media"] = l.media;
|
|
1400
|
+
if (l.as !== void 0) attrs["as"] = l.as;
|
|
1401
|
+
if (l.crossorigin !== void 0) attrs["crossorigin"] = l.crossorigin;
|
|
1402
|
+
if (l.hreflang !== void 0) attrs["hreflang"] = l.hreflang;
|
|
1403
|
+
return attrs;
|
|
1404
|
+
}
|
|
1405
|
+
function resolveHead(config) {
|
|
1406
|
+
const entries = [];
|
|
1407
|
+
if (config.charset !== void 0) {
|
|
1408
|
+
entries.push({ tag: "meta", dedupKey: "meta:charset", attrs: { charset: config.charset } });
|
|
1409
|
+
}
|
|
1410
|
+
if (config.base !== void 0) {
|
|
1411
|
+
entries.push({ tag: "base", dedupKey: "base", attrs: { href: config.base } });
|
|
1412
|
+
}
|
|
1413
|
+
if (config.title !== void 0) {
|
|
1414
|
+
entries.push({ tag: "title", dedupKey: "title", attrs: {}, text: config.title });
|
|
1415
|
+
}
|
|
1416
|
+
if (config.description !== void 0) {
|
|
1417
|
+
entries.push({
|
|
1418
|
+
tag: "meta",
|
|
1419
|
+
dedupKey: "meta:name=description",
|
|
1420
|
+
attrs: { name: "description", content: config.description }
|
|
1421
|
+
});
|
|
1422
|
+
}
|
|
1423
|
+
if (config.canonical !== void 0) {
|
|
1424
|
+
entries.push({
|
|
1425
|
+
tag: "link",
|
|
1426
|
+
dedupKey: "link:rel=canonical",
|
|
1427
|
+
attrs: { rel: "canonical", href: config.canonical }
|
|
1428
|
+
});
|
|
1429
|
+
}
|
|
1430
|
+
if (config.robots !== void 0) {
|
|
1431
|
+
entries.push({
|
|
1432
|
+
tag: "meta",
|
|
1433
|
+
dedupKey: "meta:name=robots",
|
|
1434
|
+
attrs: { name: "robots", content: config.robots }
|
|
1435
|
+
});
|
|
1436
|
+
}
|
|
1437
|
+
if (config.themeColor !== void 0) {
|
|
1438
|
+
entries.push({
|
|
1439
|
+
tag: "meta",
|
|
1440
|
+
dedupKey: "meta:name=theme-color",
|
|
1441
|
+
attrs: { name: "theme-color", content: config.themeColor }
|
|
1442
|
+
});
|
|
1443
|
+
}
|
|
1444
|
+
if (config.viewport !== void 0) {
|
|
1445
|
+
entries.push({
|
|
1446
|
+
tag: "meta",
|
|
1447
|
+
dedupKey: "meta:name=viewport",
|
|
1448
|
+
attrs: { name: "viewport", content: config.viewport }
|
|
1449
|
+
});
|
|
1450
|
+
}
|
|
1451
|
+
if (config.favicon !== void 0) {
|
|
1452
|
+
const l = typeof config.favicon === "string" ? { rel: "icon", href: config.favicon } : config.favicon;
|
|
1453
|
+
entries.push({ tag: "link", dedupKey: `link:rel=${l.rel}`, attrs: linkAttrs(l) });
|
|
1454
|
+
}
|
|
1455
|
+
if (config.openGraph !== void 0) {
|
|
1456
|
+
for (const key of Object.keys(config.openGraph)) {
|
|
1457
|
+
const property = `og:${key}`;
|
|
1458
|
+
entries.push({
|
|
1459
|
+
tag: "meta",
|
|
1460
|
+
dedupKey: `meta:property=${property}`,
|
|
1461
|
+
attrs: { property, content: config.openGraph[key] }
|
|
1462
|
+
});
|
|
1463
|
+
}
|
|
1464
|
+
}
|
|
1465
|
+
if (config.twitter !== void 0) {
|
|
1466
|
+
for (const key of Object.keys(config.twitter)) {
|
|
1467
|
+
const name = `twitter:${key}`;
|
|
1468
|
+
entries.push({
|
|
1469
|
+
tag: "meta",
|
|
1470
|
+
dedupKey: `meta:name=${name}`,
|
|
1471
|
+
attrs: { name, content: config.twitter[key] }
|
|
1472
|
+
});
|
|
1473
|
+
}
|
|
1474
|
+
}
|
|
1475
|
+
if (config.meta !== void 0) {
|
|
1476
|
+
for (const m of config.meta) {
|
|
1477
|
+
const key = metaDedupKey(m);
|
|
1478
|
+
if (key === void 0) continue;
|
|
1479
|
+
entries.push({ tag: "meta", dedupKey: key, attrs: metaAttrs(m) });
|
|
1480
|
+
}
|
|
1481
|
+
}
|
|
1482
|
+
if (config.link !== void 0) {
|
|
1483
|
+
for (const l of config.link) {
|
|
1484
|
+
entries.push({ tag: "link", dedupKey: `link:rel=${l.rel}:href=${l.href}`, attrs: linkAttrs(l) });
|
|
1485
|
+
}
|
|
1486
|
+
}
|
|
1487
|
+
return { entries };
|
|
1488
|
+
}
|
|
1489
|
+
function isHeadContribution(value) {
|
|
1490
|
+
return value !== null && typeof value === "object" && Array.isArray(value["entries"]);
|
|
1491
|
+
}
|
|
1492
|
+
|
|
1078
1493
|
// ../dsl/src/builders.ts
|
|
1079
1494
|
function isSignal(v) {
|
|
1080
1495
|
return v !== null && typeof v === "object" && typeof v["get"] === "function" && typeof v["subscribe"] === "function";
|
|
@@ -1102,6 +1517,18 @@ function applyA11yProps(props, options) {
|
|
|
1102
1517
|
if (options.ariaInvalid !== void 0) props["aria-invalid"] = String(options.ariaInvalid);
|
|
1103
1518
|
if (options.ariaRequired !== void 0) props["aria-required"] = String(options.ariaRequired);
|
|
1104
1519
|
if (options.ariaModal !== void 0) props["aria-modal"] = String(options.ariaModal);
|
|
1520
|
+
if (options.ariaOwns !== void 0) props["aria-owns"] = options.ariaOwns;
|
|
1521
|
+
if (options.ariaActiveDescendant !== void 0) props["aria-activedescendant"] = options.ariaActiveDescendant;
|
|
1522
|
+
if (options.ariaHasPopup !== void 0) props["aria-haspopup"] = String(options.ariaHasPopup);
|
|
1523
|
+
if (options.ariaSelected !== void 0) props["aria-selected"] = String(options.ariaSelected);
|
|
1524
|
+
}
|
|
1525
|
+
function registerTransition(graph, node, config) {
|
|
1526
|
+
if (config === void 0) return;
|
|
1527
|
+
const resolved = resolveTransition(config);
|
|
1528
|
+
graph.registerHandler(
|
|
1529
|
+
`__transition__${node.id}`,
|
|
1530
|
+
() => resolved
|
|
1531
|
+
);
|
|
1105
1532
|
}
|
|
1106
1533
|
function containerProps(options) {
|
|
1107
1534
|
const props = {};
|
|
@@ -1162,6 +1589,7 @@ var OVERLAY_KINDS = {
|
|
|
1162
1589
|
role: "menu",
|
|
1163
1590
|
modal: false,
|
|
1164
1591
|
takesFocus: true,
|
|
1592
|
+
menu: true,
|
|
1165
1593
|
ariaModal: false,
|
|
1166
1594
|
defaultCloseOnEscape: true,
|
|
1167
1595
|
defaultRestoreFocus: true
|
|
@@ -1294,6 +1722,7 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1294
1722
|
parent: this._node,
|
|
1295
1723
|
props: containerProps(options)
|
|
1296
1724
|
});
|
|
1725
|
+
registerTransition(this._graph, node, options.transition);
|
|
1297
1726
|
builder(new SectionBuilderImpl(node, this._graph));
|
|
1298
1727
|
}
|
|
1299
1728
|
container(key, builder, options = {}) {
|
|
@@ -1302,6 +1731,7 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1302
1731
|
parent: this._node,
|
|
1303
1732
|
props: containerProps(options)
|
|
1304
1733
|
});
|
|
1734
|
+
registerTransition(this._graph, node, options.transition);
|
|
1305
1735
|
builder(new ContainerBuilderImpl(node, this._graph));
|
|
1306
1736
|
}
|
|
1307
1737
|
list(key, builder, options = {}) {
|
|
@@ -1310,6 +1740,7 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1310
1740
|
parent: this._node,
|
|
1311
1741
|
props: containerProps(options)
|
|
1312
1742
|
});
|
|
1743
|
+
registerTransition(this._graph, node, options.transition);
|
|
1313
1744
|
builder(new ListBuilderImpl(node, this._graph));
|
|
1314
1745
|
}
|
|
1315
1746
|
listOf(key, items, renderItem, options = {}) {
|
|
@@ -1319,6 +1750,7 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1319
1750
|
parent: this._node,
|
|
1320
1751
|
props: containerProps(options)
|
|
1321
1752
|
});
|
|
1753
|
+
registerTransition(graph, node, options.transition);
|
|
1322
1754
|
const signalId = `${node.id}:items`;
|
|
1323
1755
|
node.stateRefs.push({ signalId, propKey: "items" });
|
|
1324
1756
|
graph.registerHandler(`__signal__${signalId}`, items);
|
|
@@ -1340,6 +1772,7 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1340
1772
|
}
|
|
1341
1773
|
});
|
|
1342
1774
|
renderItem(item, index, new ContainerBuilderImpl(itemNode, graph));
|
|
1775
|
+
registerTransition(graph, itemNode, options.itemTransition);
|
|
1343
1776
|
return itemNode;
|
|
1344
1777
|
};
|
|
1345
1778
|
const buildPlan = (raw) => {
|
|
@@ -1371,6 +1804,7 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1371
1804
|
parent: this._node,
|
|
1372
1805
|
props
|
|
1373
1806
|
});
|
|
1807
|
+
registerTransition(this._graph, node, options.transition);
|
|
1374
1808
|
if (options.onSubmit !== void 0) {
|
|
1375
1809
|
const handlerKey = `submit:${node.id}`;
|
|
1376
1810
|
this._graph.registerHandler(handlerKey, options.onSubmit);
|
|
@@ -1378,18 +1812,20 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1378
1812
|
}
|
|
1379
1813
|
builder(new FormBuilderImpl(node, this._graph));
|
|
1380
1814
|
}
|
|
1381
|
-
when(condition, builder, elseBuilder) {
|
|
1815
|
+
when(condition, builder, elseBuilder, options = {}) {
|
|
1382
1816
|
const graph = this._graph;
|
|
1383
1817
|
const node = graph.createNode("conditional", {
|
|
1384
1818
|
parent: this._node,
|
|
1385
1819
|
props: containerProps({})
|
|
1386
1820
|
});
|
|
1821
|
+
const branchTransition = options.transition !== void 0 && options.appear === true ? { ...options.transition, appear: true } : options.transition;
|
|
1387
1822
|
const buildBranch = (build, tag) => {
|
|
1388
1823
|
const branchKey = `when-${tag}:${node.id}`;
|
|
1389
1824
|
const branch = graph.createNode("container", {
|
|
1390
1825
|
key: branchKey,
|
|
1391
1826
|
props: { key: branchKey }
|
|
1392
1827
|
});
|
|
1828
|
+
registerTransition(graph, branch, branchTransition);
|
|
1393
1829
|
build(new ContainerBuilderImpl(branch, graph));
|
|
1394
1830
|
return branch;
|
|
1395
1831
|
};
|
|
@@ -1435,8 +1871,14 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1435
1871
|
this.container(id, (c) => {
|
|
1436
1872
|
c.when(
|
|
1437
1873
|
hasError,
|
|
1438
|
-
// Error state → fallback.
|
|
1439
|
-
|
|
1874
|
+
// Error state → fallback. The fallback branch mounts exactly when the
|
|
1875
|
+
// boundary enters its error state, so this is also where the optional
|
|
1876
|
+
// `onError` reporting hook fires (observe-only; §6/§7).
|
|
1877
|
+
(fb) => {
|
|
1878
|
+
const currentError = readError();
|
|
1879
|
+
options.onError?.(currentError);
|
|
1880
|
+
options.fallback(fb, currentError, retry);
|
|
1881
|
+
},
|
|
1440
1882
|
// Healthy state → body, guarded against synchronous build throws.
|
|
1441
1883
|
(body) => {
|
|
1442
1884
|
try {
|
|
@@ -1448,6 +1890,24 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1448
1890
|
);
|
|
1449
1891
|
}, { id });
|
|
1450
1892
|
}
|
|
1893
|
+
asyncBoundary(key, res, branches) {
|
|
1894
|
+
const isError = derived(() => res.status.get() === "error");
|
|
1895
|
+
const showSuccess = derived(
|
|
1896
|
+
() => res.status.get() !== "error" && res.data.get() !== void 0
|
|
1897
|
+
);
|
|
1898
|
+
const showLoading = derived(
|
|
1899
|
+
() => res.status.get() !== "error" && res.data.get() === void 0
|
|
1900
|
+
);
|
|
1901
|
+
const dataSignal = derived(() => res.data.get());
|
|
1902
|
+
const retry = () => {
|
|
1903
|
+
void res.refetch();
|
|
1904
|
+
};
|
|
1905
|
+
this.container(key, (c) => {
|
|
1906
|
+
c.when(isError, (fb) => branches.error?.(fb, res.error.peek(), retry));
|
|
1907
|
+
c.when(showSuccess, (sb) => branches.success(sb, dataSignal));
|
|
1908
|
+
c.when(showLoading, (lb) => branches.loading?.(lb));
|
|
1909
|
+
}, { key });
|
|
1910
|
+
}
|
|
1451
1911
|
// ── Portals & overlays ──────────────────────────────────────────────────────
|
|
1452
1912
|
portal(key, builder, options = {}) {
|
|
1453
1913
|
const node = this._graph.createNode("portal", {
|
|
@@ -1457,6 +1917,31 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1457
1917
|
});
|
|
1458
1918
|
builder(new ContainerBuilderImpl(node, this._graph));
|
|
1459
1919
|
}
|
|
1920
|
+
/**
|
|
1921
|
+
* Declare document metadata (2.0 §1–§3). Creates a `'head'` node — a neutral,
|
|
1922
|
+
* empty inline anchor at this position (one node / one element, so positional
|
|
1923
|
+
* hydration is preserved) — and registers a `__head__<id>` descriptor holding
|
|
1924
|
+
* this call's normalized, dedup-keyed {@link resolveHead} contribution. The
|
|
1925
|
+
* renderer applies it to `document.head` on the browser (adopting server tags
|
|
1926
|
+
* on hydration, cleaning up on unmount / route change) and emits the active
|
|
1927
|
+
* graph's merged metadata as a string on the server (`renderHead`).
|
|
1928
|
+
*
|
|
1929
|
+
* Multiple `head()` nodes may be live at once (app default + route + component)
|
|
1930
|
+
* — the renderer merges them and, per dedup key, the last in document order
|
|
1931
|
+
* wins (see head.ts). No new render path: this reuses the same graph-node +
|
|
1932
|
+
* handler-registry convention as overlays/transitions/components.
|
|
1933
|
+
*/
|
|
1934
|
+
head(metadata) {
|
|
1935
|
+
const node = this._graph.createNode("head", {
|
|
1936
|
+
parent: this._node,
|
|
1937
|
+
props: { "data-streetui-head-anchor": "" }
|
|
1938
|
+
});
|
|
1939
|
+
const contribution = resolveHead(metadata);
|
|
1940
|
+
this._graph.registerHandler(
|
|
1941
|
+
`__head__${node.id}`,
|
|
1942
|
+
() => contribution
|
|
1943
|
+
);
|
|
1944
|
+
}
|
|
1460
1945
|
/**
|
|
1461
1946
|
* Shared assembly for every overlay kind: a `portal` node whose single child
|
|
1462
1947
|
* is a `when(open, panel)` conditional. The panel container carries the
|
|
@@ -1484,13 +1969,24 @@ var ContainerBuilderBase = class extends ContentBuilderBase {
|
|
|
1484
1969
|
...options.ariaDescribedBy !== void 0 ? { ariaDescribedBy: options.ariaDescribedBy } : {}
|
|
1485
1970
|
};
|
|
1486
1971
|
const portalBuilder = new ContainerBuilderImpl(portalNode, graph);
|
|
1487
|
-
portalBuilder.when(
|
|
1488
|
-
|
|
1489
|
-
|
|
1972
|
+
portalBuilder.when(
|
|
1973
|
+
openSignal,
|
|
1974
|
+
(panelHost) => {
|
|
1975
|
+
panelHost.container(`${key}__panel`, builder, panelOptions);
|
|
1976
|
+
},
|
|
1977
|
+
void 0,
|
|
1978
|
+
// Overlay open/close rides the panel's `when`; a transition animates the
|
|
1979
|
+
// panel in on open and — via the reconciler's deferred-leave — plays the
|
|
1980
|
+
// leave before the panel is removed (§10). Focus is restored at close-
|
|
1981
|
+
// request time (see wireOverlayBehavior), so it never stays trapped inside
|
|
1982
|
+
// a panel that is animating away.
|
|
1983
|
+
options.transition !== void 0 ? { transition: options.transition } : {}
|
|
1984
|
+
);
|
|
1490
1985
|
const descriptor = {
|
|
1491
1986
|
open: openSignal,
|
|
1492
1987
|
modal: kind.modal,
|
|
1493
1988
|
takesFocus: kind.takesFocus,
|
|
1989
|
+
menu: kind.menu ?? false,
|
|
1494
1990
|
closeOnEscape: options.closeOnEscape ?? kind.defaultCloseOnEscape,
|
|
1495
1991
|
restoreFocus: options.restoreFocus ?? kind.defaultRestoreFocus,
|
|
1496
1992
|
...options.initialFocusId !== void 0 ? { initialFocusId: options.initialFocusId } : {},
|
|
@@ -1587,6 +2083,7 @@ var ListBuilderImpl = class extends ContentBuilderBase {
|
|
|
1587
2083
|
parent: this._node,
|
|
1588
2084
|
props: containerProps(options)
|
|
1589
2085
|
});
|
|
2086
|
+
registerTransition(this._graph, node, options.transition);
|
|
1590
2087
|
builder(new ContainerBuilderImpl(node, this._graph));
|
|
1591
2088
|
}
|
|
1592
2089
|
};
|
|
@@ -1816,8 +2313,8 @@ var RuntimeNodeInstance = class {
|
|
|
1816
2313
|
this.children.push(instance);
|
|
1817
2314
|
}
|
|
1818
2315
|
/** Subscribe to a signal and register the unsubscribe for cleanup. */
|
|
1819
|
-
trackSignal(
|
|
1820
|
-
const unsub =
|
|
2316
|
+
trackSignal(signal3, handler) {
|
|
2317
|
+
const unsub = signal3.subscribe(handler);
|
|
1821
2318
|
this.cleanup.add(unsub);
|
|
1822
2319
|
}
|
|
1823
2320
|
/** Register an arbitrary cleanup function (e.g. DOM event removal). */
|
|
@@ -2188,6 +2685,9 @@ var BrowserDOMAdapter = class {
|
|
|
2188
2685
|
body() {
|
|
2189
2686
|
return document.body ?? null;
|
|
2190
2687
|
}
|
|
2688
|
+
head() {
|
|
2689
|
+
return document.head ?? null;
|
|
2690
|
+
}
|
|
2191
2691
|
activeElement() {
|
|
2192
2692
|
return document.activeElement ?? null;
|
|
2193
2693
|
}
|
|
@@ -2567,6 +3067,9 @@ var ServerDOMAdapter = class {
|
|
|
2567
3067
|
body() {
|
|
2568
3068
|
return null;
|
|
2569
3069
|
}
|
|
3070
|
+
head() {
|
|
3071
|
+
return null;
|
|
3072
|
+
}
|
|
2570
3073
|
activeElement() {
|
|
2571
3074
|
return null;
|
|
2572
3075
|
}
|
|
@@ -2681,18 +3184,25 @@ function trapFocus(dom, container) {
|
|
|
2681
3184
|
dom.addEventListener(container, "keydown", onKeydown);
|
|
2682
3185
|
return () => dom.removeEventListener(container, "keydown", onKeydown);
|
|
2683
3186
|
}
|
|
3187
|
+
var containmentStack = [];
|
|
2684
3188
|
function containFocus(dom, container) {
|
|
2685
3189
|
const body = dom.body();
|
|
2686
3190
|
if (body === null) return () => {
|
|
2687
3191
|
};
|
|
3192
|
+
containmentStack.push(container);
|
|
2688
3193
|
const onFocusIn = (event) => {
|
|
3194
|
+
if (containmentStack[containmentStack.length - 1] !== container) return;
|
|
2689
3195
|
const target = event.target;
|
|
2690
3196
|
if (target !== null && !dom.contains(container, target)) {
|
|
2691
3197
|
focusFirst(dom, container);
|
|
2692
3198
|
}
|
|
2693
3199
|
};
|
|
2694
3200
|
dom.addEventListener(body, "focusin", onFocusIn);
|
|
2695
|
-
return () =>
|
|
3201
|
+
return () => {
|
|
3202
|
+
dom.removeEventListener(body, "focusin", onFocusIn);
|
|
3203
|
+
const index = containmentStack.lastIndexOf(container);
|
|
3204
|
+
if (index !== -1) containmentStack.splice(index, 1);
|
|
3205
|
+
};
|
|
2696
3206
|
}
|
|
2697
3207
|
function onEscape(dom, target, handler) {
|
|
2698
3208
|
const onKeydown = (event) => {
|
|
@@ -2701,6 +3211,84 @@ function onEscape(dom, target, handler) {
|
|
|
2701
3211
|
dom.addEventListener(target, "keydown", onKeydown);
|
|
2702
3212
|
return () => dom.removeEventListener(target, "keydown", onKeydown);
|
|
2703
3213
|
}
|
|
3214
|
+
function rovingMenu(dom, container, selector = FOCUSABLE_SELECTOR) {
|
|
3215
|
+
const onKeydown = (event) => {
|
|
3216
|
+
const key = event.key;
|
|
3217
|
+
const isActivate = key === "Enter" || key === " " || key === "Spacebar";
|
|
3218
|
+
const isMove = key === "ArrowDown" || key === "ArrowUp" || key === "Home" || key === "End";
|
|
3219
|
+
if (!isActivate && !isMove) return;
|
|
3220
|
+
const items = getFocusable(dom, container, selector);
|
|
3221
|
+
if (items.length === 0) return;
|
|
3222
|
+
const active = dom.activeElement();
|
|
3223
|
+
const index = active === null ? -1 : items.indexOf(active);
|
|
3224
|
+
if (isActivate) {
|
|
3225
|
+
if (index < 0) return;
|
|
3226
|
+
event.preventDefault();
|
|
3227
|
+
items[index].click?.();
|
|
3228
|
+
return;
|
|
3229
|
+
}
|
|
3230
|
+
event.preventDefault();
|
|
3231
|
+
let next;
|
|
3232
|
+
if (key === "Home") next = 0;
|
|
3233
|
+
else if (key === "End") next = items.length - 1;
|
|
3234
|
+
else if (key === "ArrowDown") next = index < 0 ? 0 : (index + 1) % items.length;
|
|
3235
|
+
else next = index <= 0 ? items.length - 1 : index - 1;
|
|
3236
|
+
dom.focus(items[next]);
|
|
3237
|
+
};
|
|
3238
|
+
dom.addEventListener(container, "keydown", onKeydown);
|
|
3239
|
+
return () => dom.removeEventListener(container, "keydown", onKeydown);
|
|
3240
|
+
}
|
|
3241
|
+
|
|
3242
|
+
// ../dom/src/live-region.ts
|
|
3243
|
+
var VISUALLY_HIDDEN = "position:absolute;width:1px;height:1px;margin:-1px;padding:0;overflow:hidden;clip:rect(0 0 0 0);white-space:nowrap;border:0;";
|
|
3244
|
+
function makeRegion(dom, politeness) {
|
|
3245
|
+
const el = dom.createElement("div");
|
|
3246
|
+
dom.setAttribute(el, "aria-live", politeness);
|
|
3247
|
+
dom.setAttribute(el, "aria-atomic", "true");
|
|
3248
|
+
dom.setAttribute(el, "role", politeness === "assertive" ? "alert" : "status");
|
|
3249
|
+
dom.setAttribute(el, "data-streetui-live", politeness);
|
|
3250
|
+
dom.setAttribute(el, "style", VISUALLY_HIDDEN);
|
|
3251
|
+
return el;
|
|
3252
|
+
}
|
|
3253
|
+
function createAnnouncer(dom) {
|
|
3254
|
+
const body = dom.body();
|
|
3255
|
+
if (body === null) {
|
|
3256
|
+
return { announce() {
|
|
3257
|
+
}, clear() {
|
|
3258
|
+
}, destroy() {
|
|
3259
|
+
} };
|
|
3260
|
+
}
|
|
3261
|
+
const polite = makeRegion(dom, "polite");
|
|
3262
|
+
const assertive = makeRegion(dom, "assertive");
|
|
3263
|
+
dom.appendChild(body, polite);
|
|
3264
|
+
dom.appendChild(body, assertive);
|
|
3265
|
+
let destroyed = false;
|
|
3266
|
+
const write = (region, message) => {
|
|
3267
|
+
dom.setTextContent(region, "");
|
|
3268
|
+
void Promise.resolve().then(() => {
|
|
3269
|
+
if (!destroyed) dom.setTextContent(region, message);
|
|
3270
|
+
});
|
|
3271
|
+
};
|
|
3272
|
+
return {
|
|
3273
|
+
announce(message, options) {
|
|
3274
|
+
if (destroyed) return;
|
|
3275
|
+
write(options?.assertive === true ? assertive : polite, message);
|
|
3276
|
+
},
|
|
3277
|
+
clear() {
|
|
3278
|
+
if (destroyed) return;
|
|
3279
|
+
dom.setTextContent(polite, "");
|
|
3280
|
+
dom.setTextContent(assertive, "");
|
|
3281
|
+
},
|
|
3282
|
+
destroy() {
|
|
3283
|
+
if (destroyed) return;
|
|
3284
|
+
destroyed = true;
|
|
3285
|
+
for (const region of [polite, assertive]) {
|
|
3286
|
+
const parent = dom.parentNode(region);
|
|
3287
|
+
if (parent !== null) dom.removeChild(parent, region);
|
|
3288
|
+
}
|
|
3289
|
+
}
|
|
3290
|
+
};
|
|
3291
|
+
}
|
|
2704
3292
|
|
|
2705
3293
|
// ../renderer/src/render-context.ts
|
|
2706
3294
|
function createRenderContext(dom, graph, container, hydrationDiagnostics, staticHTML) {
|
|
@@ -2864,7 +3452,13 @@ var TAG_MAP = {
|
|
|
2864
3452
|
// its children are relocated to a document.body container on the browser
|
|
2865
3453
|
// (see the portal branch in mount.ts). On the server (no body) it renders
|
|
2866
3454
|
// inline, so the anchor tag is what SSR/hydration positionally match on.
|
|
2867
|
-
portal: "div"
|
|
3455
|
+
portal: "div",
|
|
3456
|
+
// A `head()` node renders as a neutral, empty inline anchor <div> at its
|
|
3457
|
+
// declaration site (like a portal anchor). Its actual contribution — title/
|
|
3458
|
+
// meta/link/etc. — is applied to `document.head` by `wireHeadBehavior` on the
|
|
3459
|
+
// browser, and emitted separately by `renderHead()` on the server. Keeping a
|
|
3460
|
+
// one-node/one-element anchor preserves positional hydration.
|
|
3461
|
+
head: "div"
|
|
2868
3462
|
};
|
|
2869
3463
|
function resolveTag(type) {
|
|
2870
3464
|
return TAG_MAP[type] ?? "div";
|
|
@@ -2912,7 +3506,7 @@ function patchNode(ctx, graphNode, propKey, newValue) {
|
|
|
2912
3506
|
}
|
|
2913
3507
|
|
|
2914
3508
|
// ../renderer/src/reconciliation.ts
|
|
2915
|
-
function reconcileChildren(ctx, parentDom, oldInstances, newNodes, mountFn) {
|
|
3509
|
+
function reconcileChildren(ctx, parentDom, oldInstances, newNodes, mountFn, hooks) {
|
|
2916
3510
|
const oldByKey = /* @__PURE__ */ new Map();
|
|
2917
3511
|
for (const inst of oldInstances) {
|
|
2918
3512
|
const key = inst.graphNode.key ?? inst.graphNode.id;
|
|
@@ -2933,28 +3527,33 @@ function reconcileChildren(ctx, parentDom, oldInstances, newNodes, mountFn) {
|
|
|
2933
3527
|
}
|
|
2934
3528
|
newInstances.push(existing);
|
|
2935
3529
|
} else {
|
|
2936
|
-
const
|
|
2937
|
-
|
|
3530
|
+
const reclaimed = hooks?.takeLeaving(key);
|
|
3531
|
+
if (reclaimed !== void 0) {
|
|
3532
|
+
patchExistingInstance(ctx, reclaimed, newNode);
|
|
3533
|
+
reconcileItemChildren(ctx, reclaimed, newNode, mountFn);
|
|
3534
|
+
hooks?.onEnter(reclaimed);
|
|
3535
|
+
newInstances.push(reclaimed);
|
|
3536
|
+
} else {
|
|
3537
|
+
const inst = mountFn(newNode, parentDom);
|
|
3538
|
+
hooks?.onEnter(inst);
|
|
3539
|
+
newInstances.push(inst);
|
|
3540
|
+
}
|
|
2938
3541
|
}
|
|
2939
3542
|
}
|
|
2940
3543
|
const removed = [];
|
|
2941
3544
|
for (const inst of oldInstances) {
|
|
2942
3545
|
const key = inst.graphNode.key ?? inst.graphNode.id;
|
|
2943
|
-
if (
|
|
2944
|
-
|
|
2945
|
-
}
|
|
2946
|
-
}
|
|
2947
|
-
for (const inst of removed) {
|
|
3546
|
+
if (usedKeys.has(key)) continue;
|
|
3547
|
+
if (hooks !== void 0 && hooks.beginLeave(inst)) continue;
|
|
2948
3548
|
const parent = ctx.dom.parentNode(inst.domNode);
|
|
2949
|
-
if (parent !== null)
|
|
2950
|
-
ctx.dom.removeChild(parent, inst.domNode);
|
|
2951
|
-
}
|
|
3549
|
+
if (parent !== null) ctx.dom.removeChild(parent, inst.domNode);
|
|
2952
3550
|
inst.dispose();
|
|
3551
|
+
removed.push(inst);
|
|
2953
3552
|
}
|
|
2954
3553
|
reorderDom(ctx, parentDom, newInstances);
|
|
2955
3554
|
return { instances: newInstances, removed };
|
|
2956
3555
|
}
|
|
2957
|
-
function reconcileChildrenByPlan(ctx, parentDom, oldInstances, plan, mountFn) {
|
|
3556
|
+
function reconcileChildrenByPlan(ctx, parentDom, oldInstances, plan, mountFn, hooks) {
|
|
2958
3557
|
const oldByKey = /* @__PURE__ */ new Map();
|
|
2959
3558
|
for (const inst of oldInstances) {
|
|
2960
3559
|
oldByKey.set(inst.graphNode.key ?? inst.graphNode.id, inst);
|
|
@@ -2981,21 +3580,34 @@ function reconcileChildrenByPlan(ctx, parentDom, oldInstances, plan, mountFn) {
|
|
|
2981
3580
|
}
|
|
2982
3581
|
newInstances.push(existing);
|
|
2983
3582
|
} else {
|
|
2984
|
-
const
|
|
2985
|
-
|
|
2986
|
-
|
|
2987
|
-
|
|
3583
|
+
const reclaimed = hooks?.takeLeaving(entry.key);
|
|
3584
|
+
if (reclaimed !== void 0) {
|
|
3585
|
+
const freshNode = entry.build();
|
|
3586
|
+
built.push(freshNode);
|
|
3587
|
+
patchExistingInstance(ctx, reclaimed, freshNode);
|
|
3588
|
+
reconcileItemChildren(ctx, reclaimed, freshNode, mountFn);
|
|
3589
|
+
reclaimed.graphNode.setProp("_sig", freshNode.getProp("_sig"));
|
|
3590
|
+
reclaimed.graphNode.setProp("_item", entry.item);
|
|
3591
|
+
hooks?.onEnter(reclaimed);
|
|
3592
|
+
newInstances.push(reclaimed);
|
|
3593
|
+
} else {
|
|
3594
|
+
const freshNode = entry.build();
|
|
3595
|
+
built.push(freshNode);
|
|
3596
|
+
const inst = mountFn(freshNode, parentDom);
|
|
3597
|
+
hooks?.onEnter(inst);
|
|
3598
|
+
newInstances.push(inst);
|
|
3599
|
+
}
|
|
2988
3600
|
}
|
|
2989
3601
|
}
|
|
2990
3602
|
const removed = [];
|
|
2991
3603
|
for (const inst of oldInstances) {
|
|
2992
3604
|
const key = inst.graphNode.key ?? inst.graphNode.id;
|
|
2993
|
-
if (
|
|
2994
|
-
|
|
2995
|
-
for (const inst of removed) {
|
|
3605
|
+
if (usedKeys.has(key)) continue;
|
|
3606
|
+
if (hooks !== void 0 && hooks.beginLeave(inst)) continue;
|
|
2996
3607
|
const parent = ctx.dom.parentNode(inst.domNode);
|
|
2997
3608
|
if (parent !== null) ctx.dom.removeChild(parent, inst.domNode);
|
|
2998
3609
|
inst.dispose();
|
|
3610
|
+
removed.push(inst);
|
|
2999
3611
|
}
|
|
3000
3612
|
reorderDomMinimal(ctx, parentDom, oldInstances, newInstances);
|
|
3001
3613
|
return { instances: newInstances, removed, built };
|
|
@@ -3121,6 +3733,365 @@ function patchExistingInstance(ctx, instance, newNode) {
|
|
|
3121
3733
|
}
|
|
3122
3734
|
}
|
|
3123
3735
|
|
|
3736
|
+
// ../renderer/src/transition.ts
|
|
3737
|
+
function getResolvedTransition(graph, nodeId) {
|
|
3738
|
+
const fn = graph.getHandler(`__transition__${nodeId}`);
|
|
3739
|
+
return fn === void 0 ? void 0 : fn();
|
|
3740
|
+
}
|
|
3741
|
+
function host() {
|
|
3742
|
+
return globalThis;
|
|
3743
|
+
}
|
|
3744
|
+
function nextFrame(cb) {
|
|
3745
|
+
const h = host();
|
|
3746
|
+
const raf = h.requestAnimationFrame;
|
|
3747
|
+
if (typeof raf === "function") {
|
|
3748
|
+
raf(() => raf(cb));
|
|
3749
|
+
} else {
|
|
3750
|
+
h.setTimeout(cb, 0);
|
|
3751
|
+
}
|
|
3752
|
+
}
|
|
3753
|
+
function splitClass(value) {
|
|
3754
|
+
if (value === null) return [];
|
|
3755
|
+
const out = [];
|
|
3756
|
+
for (const t of value.split(/\s+/)) if (t.length > 0) out.push(t);
|
|
3757
|
+
return out;
|
|
3758
|
+
}
|
|
3759
|
+
function addClasses(dom, el, classes2) {
|
|
3760
|
+
if (classes2.length === 0) return;
|
|
3761
|
+
const current = splitClass(dom.getAttribute(el, "class"));
|
|
3762
|
+
let changed = false;
|
|
3763
|
+
for (const c of classes2) {
|
|
3764
|
+
if (!current.includes(c)) {
|
|
3765
|
+
current.push(c);
|
|
3766
|
+
changed = true;
|
|
3767
|
+
}
|
|
3768
|
+
}
|
|
3769
|
+
if (changed) dom.setAttribute(el, "class", current.join(" "));
|
|
3770
|
+
}
|
|
3771
|
+
function removeClasses(dom, el, classes2) {
|
|
3772
|
+
if (classes2.length === 0) return;
|
|
3773
|
+
const current = splitClass(dom.getAttribute(el, "class"));
|
|
3774
|
+
const next = current.filter((c) => !classes2.includes(c));
|
|
3775
|
+
if (next.length !== current.length) {
|
|
3776
|
+
if (next.length === 0) dom.removeAttribute(el, "class");
|
|
3777
|
+
else dom.setAttribute(el, "class", next.join(" "));
|
|
3778
|
+
}
|
|
3779
|
+
}
|
|
3780
|
+
function startRun(dom, el, active, from, to, duration, onDone) {
|
|
3781
|
+
const h = host();
|
|
3782
|
+
let finished = false;
|
|
3783
|
+
let timer = null;
|
|
3784
|
+
const onEvent = (e) => {
|
|
3785
|
+
if (e.target !== el) return;
|
|
3786
|
+
finish();
|
|
3787
|
+
};
|
|
3788
|
+
const detach = () => {
|
|
3789
|
+
dom.removeEventListener(el, "transitionend", onEvent);
|
|
3790
|
+
dom.removeEventListener(el, "animationend", onEvent);
|
|
3791
|
+
if (timer !== null) {
|
|
3792
|
+
h.clearTimeout(timer);
|
|
3793
|
+
timer = null;
|
|
3794
|
+
}
|
|
3795
|
+
};
|
|
3796
|
+
const finish = () => {
|
|
3797
|
+
if (finished) return;
|
|
3798
|
+
finished = true;
|
|
3799
|
+
detach();
|
|
3800
|
+
removeClasses(dom, el, active);
|
|
3801
|
+
removeClasses(dom, el, to);
|
|
3802
|
+
removeClasses(dom, el, from);
|
|
3803
|
+
onDone();
|
|
3804
|
+
};
|
|
3805
|
+
addClasses(dom, el, from);
|
|
3806
|
+
addClasses(dom, el, active);
|
|
3807
|
+
dom.addEventListener(el, "transitionend", onEvent);
|
|
3808
|
+
dom.addEventListener(el, "animationend", onEvent);
|
|
3809
|
+
timer = h.setTimeout(finish, duration);
|
|
3810
|
+
nextFrame(() => {
|
|
3811
|
+
if (finished) return;
|
|
3812
|
+
removeClasses(dom, el, from);
|
|
3813
|
+
addClasses(dom, el, to);
|
|
3814
|
+
});
|
|
3815
|
+
return {
|
|
3816
|
+
cancel: () => {
|
|
3817
|
+
if (finished) return;
|
|
3818
|
+
finished = true;
|
|
3819
|
+
detach();
|
|
3820
|
+
removeClasses(dom, el, active);
|
|
3821
|
+
removeClasses(dom, el, to);
|
|
3822
|
+
removeClasses(dom, el, from);
|
|
3823
|
+
}
|
|
3824
|
+
};
|
|
3825
|
+
}
|
|
3826
|
+
function runElementTransition(dom, el, rt, phase, onDone) {
|
|
3827
|
+
if (dom.body() === null || !dom.isElement(el)) {
|
|
3828
|
+
onDone();
|
|
3829
|
+
return { cancel: () => {
|
|
3830
|
+
} };
|
|
3831
|
+
}
|
|
3832
|
+
const active = phase === "enter" ? rt.enterActive : rt.leaveActive;
|
|
3833
|
+
const from = phase === "enter" ? rt.enterFrom : rt.leaveFrom;
|
|
3834
|
+
const to = phase === "enter" ? rt.enterTo : rt.leaveTo;
|
|
3835
|
+
return startRun(dom, el, active, from, to, rt.duration, onDone);
|
|
3836
|
+
}
|
|
3837
|
+
var TransitionController = class {
|
|
3838
|
+
constructor(dom, graph, finalize) {
|
|
3839
|
+
this.dom = dom;
|
|
3840
|
+
this.graph = graph;
|
|
3841
|
+
this.finalize = finalize;
|
|
3842
|
+
}
|
|
3843
|
+
leaving = /* @__PURE__ */ new Map();
|
|
3844
|
+
/** True only in a real DOM environment (browser). */
|
|
3845
|
+
get browser() {
|
|
3846
|
+
return this.dom.body() !== null;
|
|
3847
|
+
}
|
|
3848
|
+
keyOf(inst) {
|
|
3849
|
+
return inst.graphNode.key ?? inst.graphNode.id;
|
|
3850
|
+
}
|
|
3851
|
+
resolved(node) {
|
|
3852
|
+
return getResolvedTransition(this.graph, node.id);
|
|
3853
|
+
}
|
|
3854
|
+
/** Run the enter animation for `inst` if it carries a transition (browser only). */
|
|
3855
|
+
enter(inst) {
|
|
3856
|
+
if (!this.browser) return;
|
|
3857
|
+
const rt = this.resolved(inst.graphNode);
|
|
3858
|
+
if (rt === void 0) return;
|
|
3859
|
+
const el = inst.domNode;
|
|
3860
|
+
if (!this.dom.isElement(el)) return;
|
|
3861
|
+
startRun(this.dom, el, rt.enterActive, rt.enterFrom, rt.enterTo, rt.duration, () => {
|
|
3862
|
+
});
|
|
3863
|
+
}
|
|
3864
|
+
/**
|
|
3865
|
+
* Play `appear` for any initial child that opted into it (fresh browser mount
|
|
3866
|
+
* only — hydration must never animate appear, §22, and this is called only on
|
|
3867
|
+
* the mount path).
|
|
3868
|
+
*/
|
|
3869
|
+
appear(children) {
|
|
3870
|
+
if (!this.browser) return;
|
|
3871
|
+
for (const child of children) {
|
|
3872
|
+
const rt = this.resolved(child.graphNode);
|
|
3873
|
+
if (rt !== void 0 && rt.appear) this.enter(child);
|
|
3874
|
+
}
|
|
3875
|
+
}
|
|
3876
|
+
hooks() {
|
|
3877
|
+
return {
|
|
3878
|
+
takeLeaving: (key) => {
|
|
3879
|
+
const entry = this.leaving.get(key);
|
|
3880
|
+
if (entry === void 0) return void 0;
|
|
3881
|
+
entry.run.cancel();
|
|
3882
|
+
this.leaving.delete(key);
|
|
3883
|
+
return entry.inst;
|
|
3884
|
+
},
|
|
3885
|
+
beginLeave: (inst) => {
|
|
3886
|
+
if (!this.browser) return false;
|
|
3887
|
+
const rt = this.resolved(inst.graphNode);
|
|
3888
|
+
if (rt === void 0) return false;
|
|
3889
|
+
const el = inst.domNode;
|
|
3890
|
+
if (!this.dom.isElement(el)) return false;
|
|
3891
|
+
const key = this.keyOf(inst);
|
|
3892
|
+
const prior = this.leaving.get(key);
|
|
3893
|
+
if (prior !== void 0) prior.run.cancel();
|
|
3894
|
+
const run = startRun(
|
|
3895
|
+
this.dom,
|
|
3896
|
+
el,
|
|
3897
|
+
rt.leaveActive,
|
|
3898
|
+
rt.leaveFrom,
|
|
3899
|
+
rt.leaveTo,
|
|
3900
|
+
rt.duration,
|
|
3901
|
+
() => {
|
|
3902
|
+
const current = this.leaving.get(key);
|
|
3903
|
+
if (current !== void 0 && current.run === run) {
|
|
3904
|
+
this.leaving.delete(key);
|
|
3905
|
+
this.finalize(inst);
|
|
3906
|
+
}
|
|
3907
|
+
}
|
|
3908
|
+
);
|
|
3909
|
+
this.leaving.set(key, { inst, run });
|
|
3910
|
+
return true;
|
|
3911
|
+
},
|
|
3912
|
+
onEnter: (inst) => this.enter(inst)
|
|
3913
|
+
};
|
|
3914
|
+
}
|
|
3915
|
+
};
|
|
3916
|
+
|
|
3917
|
+
// ../renderer/src/head.ts
|
|
3918
|
+
var HEAD_MARKER = "data-streetui-head";
|
|
3919
|
+
var HEAD_KEY = "data-streetui-head-key";
|
|
3920
|
+
function isSignalLike(v) {
|
|
3921
|
+
return v !== null && typeof v === "object" && typeof v["subscribe"] === "function" && typeof v["peek"] === "function";
|
|
3922
|
+
}
|
|
3923
|
+
function readValue(v) {
|
|
3924
|
+
if (isSignalLike(v)) return String(v.peek() ?? "");
|
|
3925
|
+
return String(v ?? "");
|
|
3926
|
+
}
|
|
3927
|
+
function resolveEntry(entry) {
|
|
3928
|
+
const attrs = {};
|
|
3929
|
+
for (const key of Object.keys(entry.attrs)) {
|
|
3930
|
+
attrs[key] = readValue(entry.attrs[key]);
|
|
3931
|
+
}
|
|
3932
|
+
const resolved = { tag: entry.tag, attrs };
|
|
3933
|
+
if (entry.tag === "title") {
|
|
3934
|
+
return { ...resolved, text: readValue(entry.text) };
|
|
3935
|
+
}
|
|
3936
|
+
return resolved;
|
|
3937
|
+
}
|
|
3938
|
+
var HeadManager = class {
|
|
3939
|
+
_dom;
|
|
3940
|
+
_head;
|
|
3941
|
+
_contributions = /* @__PURE__ */ new Map();
|
|
3942
|
+
_applied = /* @__PURE__ */ new Map();
|
|
3943
|
+
_order = 0;
|
|
3944
|
+
_adopted = false;
|
|
3945
|
+
constructor(dom, head) {
|
|
3946
|
+
this._dom = dom;
|
|
3947
|
+
this._head = head;
|
|
3948
|
+
}
|
|
3949
|
+
/** Register (or replace) a node's contribution and re-apply the merged result. */
|
|
3950
|
+
register(nodeId, entries) {
|
|
3951
|
+
this._contributions.set(nodeId, { order: this._order++, entries });
|
|
3952
|
+
this.apply();
|
|
3953
|
+
}
|
|
3954
|
+
/** Withdraw a node's contribution (unmount / route change) and re-apply. */
|
|
3955
|
+
unregister(nodeId) {
|
|
3956
|
+
if (this._contributions.delete(nodeId)) this.apply();
|
|
3957
|
+
}
|
|
3958
|
+
/** Recompute the merged head and patch `document.head` to match. */
|
|
3959
|
+
apply() {
|
|
3960
|
+
if (!this._adopted) {
|
|
3961
|
+
this._adoptServerTags();
|
|
3962
|
+
this._adopted = true;
|
|
3963
|
+
}
|
|
3964
|
+
const ordered = [...this._contributions.values()].sort((a, b) => a.order - b.order);
|
|
3965
|
+
const merged = /* @__PURE__ */ new Map();
|
|
3966
|
+
for (const contribution of ordered) {
|
|
3967
|
+
for (const entry of contribution.entries) {
|
|
3968
|
+
merged.set(entry.dedupKey, resolveEntry(entry));
|
|
3969
|
+
}
|
|
3970
|
+
}
|
|
3971
|
+
for (const [key, desired] of merged) {
|
|
3972
|
+
const existing = this._applied.get(key);
|
|
3973
|
+
if (existing !== void 0 && existing.tag === desired.tag) {
|
|
3974
|
+
this._reconcileAttrs(existing, desired);
|
|
3975
|
+
} else {
|
|
3976
|
+
if (existing !== void 0) {
|
|
3977
|
+
this._dom.removeChild(this._head, existing.el);
|
|
3978
|
+
this._applied.delete(key);
|
|
3979
|
+
}
|
|
3980
|
+
const el = this._createTag(key, desired);
|
|
3981
|
+
this._dom.appendChild(this._head, el);
|
|
3982
|
+
this._applied.set(key, { el, attrKeys: new Set(Object.keys(desired.attrs)), tag: desired.tag });
|
|
3983
|
+
}
|
|
3984
|
+
}
|
|
3985
|
+
for (const [key, record] of [...this._applied]) {
|
|
3986
|
+
if (!merged.has(key)) {
|
|
3987
|
+
this._dom.removeChild(this._head, record.el);
|
|
3988
|
+
this._applied.delete(key);
|
|
3989
|
+
}
|
|
3990
|
+
}
|
|
3991
|
+
}
|
|
3992
|
+
_createTag(key, desired) {
|
|
3993
|
+
const el = this._dom.createElement(desired.tag);
|
|
3994
|
+
this._dom.setAttribute(el, HEAD_MARKER, "");
|
|
3995
|
+
this._dom.setAttribute(el, HEAD_KEY, key);
|
|
3996
|
+
for (const attr of Object.keys(desired.attrs)) {
|
|
3997
|
+
this._dom.setAttribute(el, attr, desired.attrs[attr]);
|
|
3998
|
+
}
|
|
3999
|
+
if (desired.tag === "title") this._dom.setTextContent(el, desired.text ?? "");
|
|
4000
|
+
return el;
|
|
4001
|
+
}
|
|
4002
|
+
_reconcileAttrs(record, desired) {
|
|
4003
|
+
const nextKeys = new Set(Object.keys(desired.attrs));
|
|
4004
|
+
for (const attr of record.attrKeys) {
|
|
4005
|
+
if (!nextKeys.has(attr)) this._dom.removeAttribute(record.el, attr);
|
|
4006
|
+
}
|
|
4007
|
+
for (const attr of nextKeys) {
|
|
4008
|
+
this._dom.setAttribute(record.el, attr, desired.attrs[attr]);
|
|
4009
|
+
}
|
|
4010
|
+
if (desired.tag === "title") this._dom.setTextContent(record.el, desired.text ?? "");
|
|
4011
|
+
record.attrKeys = nextKeys;
|
|
4012
|
+
}
|
|
4013
|
+
/**
|
|
4014
|
+
* Seed `_applied` from server-emitted `[data-streetui-head-key]` tags already
|
|
4015
|
+
* in `document.head`. The subsequent diff reuses these elements when the
|
|
4016
|
+
* client desires the same key (no duplicate), rewrites them if the value
|
|
4017
|
+
* changed, or removes them if the client graph no longer wants them.
|
|
4018
|
+
*/
|
|
4019
|
+
_adoptServerTags() {
|
|
4020
|
+
for (const child of this._dom.childNodes(this._head)) {
|
|
4021
|
+
if (!this._dom.isElement(child)) continue;
|
|
4022
|
+
const el = child;
|
|
4023
|
+
const key = this._dom.getAttribute(el, HEAD_KEY);
|
|
4024
|
+
if (key === null) continue;
|
|
4025
|
+
this._applied.set(key, {
|
|
4026
|
+
el,
|
|
4027
|
+
attrKeys: new Set(this._attrNames(el)),
|
|
4028
|
+
tag: this._dom.tagName(el)
|
|
4029
|
+
});
|
|
4030
|
+
}
|
|
4031
|
+
}
|
|
4032
|
+
/** The framework-managed attribute names currently on a server tag. */
|
|
4033
|
+
_attrNames(el) {
|
|
4034
|
+
const names = [];
|
|
4035
|
+
if (this._dom.getAttribute(el, HEAD_MARKER) !== null) names.push(HEAD_MARKER);
|
|
4036
|
+
if (this._dom.getAttribute(el, HEAD_KEY) !== null) names.push(HEAD_KEY);
|
|
4037
|
+
return names;
|
|
4038
|
+
}
|
|
4039
|
+
};
|
|
4040
|
+
function getHeadManager(ctx) {
|
|
4041
|
+
const head = ctx.dom.head();
|
|
4042
|
+
if (head === null) return null;
|
|
4043
|
+
const mutable = ctx;
|
|
4044
|
+
if (mutable.head === void 0) mutable.head = new HeadManager(ctx.dom, head);
|
|
4045
|
+
return mutable.head;
|
|
4046
|
+
}
|
|
4047
|
+
function wireHeadBehavior(ctx, graphNode, instance) {
|
|
4048
|
+
const manager = getHeadManager(ctx);
|
|
4049
|
+
if (manager === null) return;
|
|
4050
|
+
const descFn = ctx.graph.getHandler(`__head__${graphNode.id}`);
|
|
4051
|
+
if (descFn === void 0) return;
|
|
4052
|
+
const contribution = descFn();
|
|
4053
|
+
const nodeId = graphNode.id;
|
|
4054
|
+
manager.register(nodeId, contribution.entries);
|
|
4055
|
+
for (const entry of contribution.entries) {
|
|
4056
|
+
for (const attrKey of Object.keys(entry.attrs)) {
|
|
4057
|
+
const v = entry.attrs[attrKey];
|
|
4058
|
+
if (isSignalLike(v)) {
|
|
4059
|
+
instance.trackCleanup(v.subscribe(() => manager.apply()));
|
|
4060
|
+
}
|
|
4061
|
+
}
|
|
4062
|
+
if (isSignalLike(entry.text)) {
|
|
4063
|
+
instance.trackCleanup(entry.text.subscribe(() => manager.apply()));
|
|
4064
|
+
}
|
|
4065
|
+
}
|
|
4066
|
+
instance.trackCleanup(() => manager.unregister(nodeId));
|
|
4067
|
+
}
|
|
4068
|
+
function renderHead(compiled) {
|
|
4069
|
+
const graph = compiled.graph;
|
|
4070
|
+
const merged = /* @__PURE__ */ new Map();
|
|
4071
|
+
graph.walk((node) => {
|
|
4072
|
+
if (node.type !== "head") return;
|
|
4073
|
+
const descFn = graph.getHandler(`__head__${node.id}`);
|
|
4074
|
+
if (descFn === void 0) return;
|
|
4075
|
+
for (const entry of descFn().entries) {
|
|
4076
|
+
merged.set(entry.dedupKey, resolveEntry(entry));
|
|
4077
|
+
}
|
|
4078
|
+
});
|
|
4079
|
+
if (merged.size === 0) return "";
|
|
4080
|
+
const dom = new ServerDOMAdapter();
|
|
4081
|
+
let out = "";
|
|
4082
|
+
for (const [key, desired] of merged) {
|
|
4083
|
+
const el = dom.createElement(desired.tag);
|
|
4084
|
+
dom.setAttribute(el, HEAD_MARKER, "");
|
|
4085
|
+
dom.setAttribute(el, HEAD_KEY, key);
|
|
4086
|
+
for (const attr of Object.keys(desired.attrs)) {
|
|
4087
|
+
dom.setAttribute(el, attr, desired.attrs[attr]);
|
|
4088
|
+
}
|
|
4089
|
+
if (desired.tag === "title") dom.setTextContent(el, desired.text ?? "");
|
|
4090
|
+
out += dom.serializeOuter(el);
|
|
4091
|
+
}
|
|
4092
|
+
return out;
|
|
4093
|
+
}
|
|
4094
|
+
|
|
3124
4095
|
// ../renderer/src/mount.ts
|
|
3125
4096
|
var SKIP_PROP_KEYS = /* @__PURE__ */ new Set([
|
|
3126
4097
|
"text",
|
|
@@ -3243,6 +4214,9 @@ function mountNode(ctx, graphNode, parentDom) {
|
|
|
3243
4214
|
const instance2 = new NodeInstance(graphNode, el2);
|
|
3244
4215
|
ctx.instances.set(graphNode.id, instance2);
|
|
3245
4216
|
wireEvents(dom, graph, graphNode, el2, instance2);
|
|
4217
|
+
if (graphNode.stateRefs.length !== 0) {
|
|
4218
|
+
wireSignalBindings(ctx, graphNode, instance2, linkUpdate(dom, el2));
|
|
4219
|
+
}
|
|
3246
4220
|
dom.appendChild(parentDom, el2);
|
|
3247
4221
|
return instance2;
|
|
3248
4222
|
}
|
|
@@ -3273,7 +4247,7 @@ function mountNode(ctx, graphNode, parentDom) {
|
|
|
3273
4247
|
instance2.addChild(childInstance);
|
|
3274
4248
|
}
|
|
3275
4249
|
dom.appendChild(parentDom, el2);
|
|
3276
|
-
wireReactiveList(ctx, graphNode, instance2, el2);
|
|
4250
|
+
wireReactiveList(ctx, graphNode, instance2, el2, true);
|
|
3277
4251
|
return instance2;
|
|
3278
4252
|
}
|
|
3279
4253
|
if (graphNode.type === "portal") {
|
|
@@ -3298,6 +4272,16 @@ function mountNode(ctx, graphNode, parentDom) {
|
|
|
3298
4272
|
wireOverlayBehavior(ctx, graphNode, instance2, target);
|
|
3299
4273
|
return instance2;
|
|
3300
4274
|
}
|
|
4275
|
+
if (graphNode.type === "head") {
|
|
4276
|
+
const anchor = dom.createElement(resolveTag("head"));
|
|
4277
|
+
dom.setAttribute(anchor, "data-streetui-head-anchor", "");
|
|
4278
|
+
applyNodeProps(ctx, graphNode, anchor);
|
|
4279
|
+
const instance2 = new NodeInstance(graphNode, anchor);
|
|
4280
|
+
ctx.instances.set(graphNode.id, instance2);
|
|
4281
|
+
dom.appendChild(parentDom, anchor);
|
|
4282
|
+
wireHeadBehavior(ctx, graphNode, instance2);
|
|
4283
|
+
return instance2;
|
|
4284
|
+
}
|
|
3301
4285
|
const tag = resolveTag(graphNode.type);
|
|
3302
4286
|
const el = dom.createElement(tag);
|
|
3303
4287
|
applyNodeProps(ctx, graphNode, el);
|
|
@@ -3362,6 +4346,17 @@ function buttonUpdate(dom, el) {
|
|
|
3362
4346
|
}
|
|
3363
4347
|
};
|
|
3364
4348
|
}
|
|
4349
|
+
function linkUpdate(dom, el) {
|
|
4350
|
+
return (propKey, value) => {
|
|
4351
|
+
if (propKey === "label") {
|
|
4352
|
+
dom.setTextContent(el, String(value ?? ""));
|
|
4353
|
+
} else if (propKey === "href") {
|
|
4354
|
+
dom.setAttribute(el, "href", String(value ?? ""));
|
|
4355
|
+
} else {
|
|
4356
|
+
applyProp(dom, el, propKey, value);
|
|
4357
|
+
}
|
|
4358
|
+
};
|
|
4359
|
+
}
|
|
3365
4360
|
function applyNodeProps(ctx, graphNode, el) {
|
|
3366
4361
|
const props = graphNode.props;
|
|
3367
4362
|
for (const key in props) {
|
|
@@ -3382,32 +4377,42 @@ function wireSignalBindings(ctx, graphNode, instance, onUpdate) {
|
|
|
3382
4377
|
instance.trackCleanup(unsub);
|
|
3383
4378
|
}
|
|
3384
4379
|
}
|
|
3385
|
-
function wireReactiveList(ctx, graphNode, instance, el) {
|
|
4380
|
+
function wireReactiveList(ctx, graphNode, instance, el, runAppear = false) {
|
|
3386
4381
|
const plan = ctx.graph.getHandler(`__listplan__${graphNode.id}`);
|
|
3387
4382
|
const build = ctx.graph.getHandler(`__listbuild__${graphNode.id}`);
|
|
3388
4383
|
if (plan === void 0 && build === void 0) return;
|
|
4384
|
+
const controller = new TransitionController(ctx.dom, ctx.graph, (leaving) => {
|
|
4385
|
+
const parent = ctx.dom.parentNode(leaving.domNode);
|
|
4386
|
+
if (parent !== null) ctx.dom.removeChild(parent, leaving.domNode);
|
|
4387
|
+
leaving.dispose();
|
|
4388
|
+
forgetInstance(ctx, leaving);
|
|
4389
|
+
ctx.graph.detachNode(leaving.graphNode);
|
|
4390
|
+
});
|
|
4391
|
+
const hooks = controller.hooks();
|
|
4392
|
+
if (runAppear) controller.appear(instance.children);
|
|
3389
4393
|
for (const stateRef of graphNode.stateRefs) {
|
|
3390
4394
|
if (stateRef.propKey !== "items") continue;
|
|
3391
4395
|
const sig = ctx.graph.getHandler(`__signal__${stateRef.signalId}`);
|
|
3392
4396
|
if (sig === void 0 || typeof sig.subscribe !== "function") continue;
|
|
3393
4397
|
const unsub = sig.subscribe((value) => {
|
|
3394
4398
|
if (plan !== void 0) {
|
|
3395
|
-
reconcileReactiveListByPlan(ctx, graphNode, instance, el, plan(value));
|
|
4399
|
+
reconcileReactiveListByPlan(ctx, graphNode, instance, el, plan(value), hooks);
|
|
3396
4400
|
} else {
|
|
3397
|
-
reconcileReactiveList(ctx, graphNode, instance, el, build(value));
|
|
4401
|
+
reconcileReactiveList(ctx, graphNode, instance, el, build(value), hooks);
|
|
3398
4402
|
}
|
|
3399
4403
|
});
|
|
3400
4404
|
instance.trackCleanup(unsub);
|
|
3401
4405
|
}
|
|
3402
4406
|
}
|
|
3403
|
-
function reconcileReactiveListByPlan(ctx, listNode, listInstance, listEl, plan) {
|
|
4407
|
+
function reconcileReactiveListByPlan(ctx, listNode, listInstance, listEl, plan, hooks) {
|
|
3404
4408
|
const oldInstances = [...listInstance.children];
|
|
3405
4409
|
const result = reconcileChildrenByPlan(
|
|
3406
4410
|
ctx,
|
|
3407
4411
|
listEl,
|
|
3408
4412
|
oldInstances,
|
|
3409
4413
|
plan,
|
|
3410
|
-
(node, parent) => mountNode(ctx, node, parent)
|
|
4414
|
+
(node, parent) => mountNode(ctx, node, parent),
|
|
4415
|
+
hooks
|
|
3411
4416
|
);
|
|
3412
4417
|
listInstance.children.length = 0;
|
|
3413
4418
|
for (const inst of result.instances) listInstance.children.push(inst);
|
|
@@ -3422,14 +4427,15 @@ function reconcileReactiveListByPlan(ctx, listNode, listInstance, listEl, plan)
|
|
|
3422
4427
|
for (const child of [...listNode.children]) listNode.removeChild(child);
|
|
3423
4428
|
for (const inst of result.instances) listNode.appendChild(inst.graphNode);
|
|
3424
4429
|
}
|
|
3425
|
-
function reconcileReactiveList(ctx, listNode, listInstance, listEl, newNodes) {
|
|
4430
|
+
function reconcileReactiveList(ctx, listNode, listInstance, listEl, newNodes, hooks) {
|
|
3426
4431
|
const oldInstances = [...listInstance.children];
|
|
3427
4432
|
const result = reconcileChildren(
|
|
3428
4433
|
ctx,
|
|
3429
4434
|
listEl,
|
|
3430
4435
|
oldInstances,
|
|
3431
4436
|
newNodes,
|
|
3432
|
-
(node, parent) => mountNode(ctx, node, parent)
|
|
4437
|
+
(node, parent) => mountNode(ctx, node, parent),
|
|
4438
|
+
hooks
|
|
3433
4439
|
);
|
|
3434
4440
|
listInstance.children.length = 0;
|
|
3435
4441
|
for (const inst of result.instances) listInstance.children.push(inst);
|
|
@@ -3465,11 +4471,14 @@ function wireOverlayBehavior(ctx, graphNode, instance, target) {
|
|
|
3465
4471
|
const onOpenChange = (isOpen) => {
|
|
3466
4472
|
if (isOpen) {
|
|
3467
4473
|
if (desc.restoreFocus) saved = saveFocus(dom);
|
|
3468
|
-
if (desc.takesFocus) focusInitial(dom, target, desc.initialFocusId);
|
|
3469
4474
|
if (desc.modal) {
|
|
3470
4475
|
active.push(trapFocus(dom, target));
|
|
3471
4476
|
active.push(containFocus(dom, target));
|
|
3472
4477
|
}
|
|
4478
|
+
if (desc.menu) {
|
|
4479
|
+
active.push(rovingMenu(dom, target));
|
|
4480
|
+
}
|
|
4481
|
+
if (desc.takesFocus) focusInitial(dom, target, desc.initialFocusId);
|
|
3473
4482
|
if (desc.closeOnEscape && desc.onClose !== void 0) {
|
|
3474
4483
|
active.push(onEscape(dom, target, desc.onClose));
|
|
3475
4484
|
}
|
|
@@ -3582,7 +4591,12 @@ function hydrateNode(ctx, graphNode, domNode, path) {
|
|
|
3582
4591
|
case "link": {
|
|
3583
4592
|
const instance = new NodeInstance(graphNode, domNode);
|
|
3584
4593
|
ctx.instances.set(graphNode.id, instance);
|
|
3585
|
-
if (graphNode.type === "link")
|
|
4594
|
+
if (graphNode.type === "link") {
|
|
4595
|
+
wireEvents(dom, graph, graphNode, domNode, instance);
|
|
4596
|
+
if (graphNode.stateRefs.length !== 0) {
|
|
4597
|
+
wireSignalBindings(ctx, graphNode, instance, linkUpdate(dom, domNode));
|
|
4598
|
+
}
|
|
4599
|
+
}
|
|
3586
4600
|
return instance;
|
|
3587
4601
|
}
|
|
3588
4602
|
case "reactive-list":
|
|
@@ -3612,6 +4626,12 @@ function hydrateNode(ctx, graphNode, domNode, path) {
|
|
|
3612
4626
|
wireOverlayBehavior(ctx, graphNode, instance, target);
|
|
3613
4627
|
return instance;
|
|
3614
4628
|
}
|
|
4629
|
+
case "head": {
|
|
4630
|
+
const instance = new NodeInstance(graphNode, domNode);
|
|
4631
|
+
ctx.instances.set(graphNode.id, instance);
|
|
4632
|
+
wireHeadBehavior(ctx, graphNode, instance);
|
|
4633
|
+
return instance;
|
|
4634
|
+
}
|
|
3615
4635
|
default: {
|
|
3616
4636
|
const instance = new NodeInstance(graphNode, domNode);
|
|
3617
4637
|
ctx.instances.set(graphNode.id, instance);
|
|
@@ -3858,7 +4878,8 @@ function analyzeGraph(graph) {
|
|
|
3858
4878
|
const isConditional = node.type === "conditional";
|
|
3859
4879
|
const isPortal = node.type === "portal";
|
|
3860
4880
|
const isComponent = node.type === "component";
|
|
3861
|
-
const
|
|
4881
|
+
const isHead = node.type === "head";
|
|
4882
|
+
const isStatic = node.stateRefs.length === 0 && !hasEvents && !isList && !isConditional && !isPortal && !isComponent && !isHead;
|
|
3862
4883
|
const isStaticSubtree = isStatic && allChildrenStatic;
|
|
3863
4884
|
nodes.set(node.id, {
|
|
3864
4885
|
isStatic,
|
|
@@ -4204,16 +5225,38 @@ function mountRouter(router, options) {
|
|
|
4204
5225
|
} else {
|
|
4205
5226
|
outlet = container;
|
|
4206
5227
|
}
|
|
5228
|
+
const routeTransition = options.transition !== void 0 ? resolveTransition(options.transition) : void 0;
|
|
5229
|
+
const txDom = routeTransition !== void 0 ? new BrowserDOMAdapter() : void 0;
|
|
4207
5230
|
let active = null;
|
|
5231
|
+
const pendingLeaves = /* @__PURE__ */ new Map();
|
|
4208
5232
|
let firstRender = hydrateMode;
|
|
5233
|
+
const teardownRoute = (route) => {
|
|
5234
|
+
route.registry.run();
|
|
5235
|
+
route.mounted.unmount();
|
|
5236
|
+
if (route.host !== null && txDom !== void 0) {
|
|
5237
|
+
const parent = txDom.parentNode(route.host);
|
|
5238
|
+
if (parent !== null) txDom.removeChild(parent, route.host);
|
|
5239
|
+
}
|
|
5240
|
+
};
|
|
4209
5241
|
const disposeActive = () => {
|
|
4210
5242
|
if (active === null) return;
|
|
4211
|
-
active
|
|
4212
|
-
active.mounted.unmount();
|
|
5243
|
+
teardownRoute(active);
|
|
4213
5244
|
active = null;
|
|
4214
5245
|
};
|
|
4215
|
-
const
|
|
4216
|
-
|
|
5246
|
+
const wrapOutletChildren = (dom) => {
|
|
5247
|
+
const host2 = dom.createElement("div");
|
|
5248
|
+
dom.setAttribute(host2, "data-streetui-route", "");
|
|
5249
|
+
const moved = [];
|
|
5250
|
+
let child = dom.firstChild(outlet);
|
|
5251
|
+
while (child !== null) {
|
|
5252
|
+
moved.push(child);
|
|
5253
|
+
child = dom.nextSibling(child);
|
|
5254
|
+
}
|
|
5255
|
+
for (const n of moved) dom.appendChild(host2, n);
|
|
5256
|
+
dom.appendChild(outlet, host2);
|
|
5257
|
+
return host2;
|
|
5258
|
+
};
|
|
5259
|
+
const buildRoute = (match, target, hydrate) => {
|
|
4217
5260
|
const registry = new CleanupRegistry();
|
|
4218
5261
|
const ctx = {
|
|
4219
5262
|
path: match.path,
|
|
@@ -4226,9 +5269,53 @@ function mountRouter(router, options) {
|
|
|
4226
5269
|
routeApp.page("route", (page) => match.route.builder(page, ctx));
|
|
4227
5270
|
const runtime = createRuntime({ renderer });
|
|
4228
5271
|
const routeCompiled = compile(routeApp);
|
|
4229
|
-
const mounted =
|
|
5272
|
+
const mounted = hydrate ? runtime.hydrate(routeCompiled, target) : runtime.mount(routeCompiled, target);
|
|
5273
|
+
return { registry, mounted, host: null, enterRun: null };
|
|
5274
|
+
};
|
|
5275
|
+
const renderRoute = (match) => {
|
|
5276
|
+
if (routeTransition === void 0 || txDom === void 0) {
|
|
5277
|
+
disposeActive();
|
|
5278
|
+
active = buildRoute(match, outlet, firstRender);
|
|
5279
|
+
firstRender = false;
|
|
5280
|
+
return;
|
|
5281
|
+
}
|
|
5282
|
+
if (active === null) {
|
|
5283
|
+
if (firstRender) {
|
|
5284
|
+
active = buildRoute(match, outlet, true);
|
|
5285
|
+
active.host = wrapOutletChildren(txDom);
|
|
5286
|
+
} else {
|
|
5287
|
+
const host2 = txDom.createElement("div");
|
|
5288
|
+
txDom.setAttribute(host2, "data-streetui-route", "");
|
|
5289
|
+
txDom.appendChild(outlet, host2);
|
|
5290
|
+
active = buildRoute(match, host2, false);
|
|
5291
|
+
active.host = host2;
|
|
5292
|
+
}
|
|
5293
|
+
firstRender = false;
|
|
5294
|
+
return;
|
|
5295
|
+
}
|
|
4230
5296
|
firstRender = false;
|
|
4231
|
-
|
|
5297
|
+
const leaving = active;
|
|
5298
|
+
leaving.enterRun?.cancel();
|
|
5299
|
+
leaving.enterRun = null;
|
|
5300
|
+
const leaveHost = leaving.host;
|
|
5301
|
+
const enterHost = txDom.createElement("div");
|
|
5302
|
+
txDom.setAttribute(enterHost, "data-streetui-route", "");
|
|
5303
|
+
txDom.appendChild(outlet, enterHost);
|
|
5304
|
+
const next = buildRoute(match, enterHost, false);
|
|
5305
|
+
next.host = enterHost;
|
|
5306
|
+
next.enterRun = runElementTransition(txDom, enterHost, routeTransition, "enter", () => {
|
|
5307
|
+
next.enterRun = null;
|
|
5308
|
+
});
|
|
5309
|
+
active = next;
|
|
5310
|
+
if (leaveHost !== null) {
|
|
5311
|
+
const run = runElementTransition(txDom, leaveHost, routeTransition, "leave", () => {
|
|
5312
|
+
pendingLeaves.delete(leaving);
|
|
5313
|
+
teardownRoute(leaving);
|
|
5314
|
+
});
|
|
5315
|
+
pendingLeaves.set(leaving, run);
|
|
5316
|
+
} else {
|
|
5317
|
+
teardownRoute(leaving);
|
|
5318
|
+
}
|
|
4232
5319
|
};
|
|
4233
5320
|
renderRoute(router.currentRoute.peek());
|
|
4234
5321
|
const stopRouteSub = router.currentRoute.subscribe((match) => renderRoute(match));
|
|
@@ -4256,6 +5343,11 @@ function mountRouter(router, options) {
|
|
|
4256
5343
|
unmount() {
|
|
4257
5344
|
if (interceptLinks) container.removeEventListener("click", onClick);
|
|
4258
5345
|
stopRouteSub();
|
|
5346
|
+
for (const [route, run] of pendingLeaves) {
|
|
5347
|
+
run.cancel();
|
|
5348
|
+
teardownRoute(route);
|
|
5349
|
+
}
|
|
5350
|
+
pendingLeaves.clear();
|
|
4259
5351
|
disposeActive();
|
|
4260
5352
|
shellMounted?.unmount();
|
|
4261
5353
|
router.destroy();
|
|
@@ -4580,6 +5672,40 @@ function inspectComponents(graph) {
|
|
|
4580
5672
|
});
|
|
4581
5673
|
return out;
|
|
4582
5674
|
}
|
|
5675
|
+
function inspectInteractions(graph) {
|
|
5676
|
+
const overlays = [];
|
|
5677
|
+
const transitions = [];
|
|
5678
|
+
graph.walk((node, depth) => {
|
|
5679
|
+
const overlayFn = graph.getHandler(`__overlay__${node.id}`);
|
|
5680
|
+
if (overlayFn !== void 0) {
|
|
5681
|
+
const d = overlayFn();
|
|
5682
|
+
overlays.push({
|
|
5683
|
+
id: node.id,
|
|
5684
|
+
key: node.key,
|
|
5685
|
+
open: d.open.peek(),
|
|
5686
|
+
modal: d.modal,
|
|
5687
|
+
takesFocus: d.takesFocus,
|
|
5688
|
+
menu: d.menu,
|
|
5689
|
+
closeOnEscape: d.closeOnEscape,
|
|
5690
|
+
restoreFocus: d.restoreFocus,
|
|
5691
|
+
depth
|
|
5692
|
+
});
|
|
5693
|
+
}
|
|
5694
|
+
const transitionFn = graph.getHandler(`__transition__${node.id}`);
|
|
5695
|
+
if (transitionFn !== void 0) {
|
|
5696
|
+
const t = transitionFn();
|
|
5697
|
+
transitions.push({
|
|
5698
|
+
id: node.id,
|
|
5699
|
+
key: node.key,
|
|
5700
|
+
nodeType: node.type,
|
|
5701
|
+
duration: t.duration,
|
|
5702
|
+
appear: t.appear,
|
|
5703
|
+
depth
|
|
5704
|
+
});
|
|
5705
|
+
}
|
|
5706
|
+
});
|
|
5707
|
+
return { overlays, transitions };
|
|
5708
|
+
}
|
|
4583
5709
|
|
|
4584
5710
|
// ../devtools/src/application.ts
|
|
4585
5711
|
function collectPerf(node, distinctSignals, acc) {
|
|
@@ -4815,11 +5941,22 @@ function capture(compiled, sources, options) {
|
|
|
4815
5941
|
snapshot: app.perf,
|
|
4816
5942
|
diagnostics: diagnosePerformance(compiled, options.perfThresholds)
|
|
4817
5943
|
};
|
|
5944
|
+
const components = inspectComponents(compiled.graph);
|
|
5945
|
+
const interactions = inspectInteractions(compiled.graph);
|
|
5946
|
+
const diagnostics = {
|
|
5947
|
+
errors: app.diagnostics.errors,
|
|
5948
|
+
warnings: app.diagnostics.warnings,
|
|
5949
|
+
messages: app.diagnostics.messages
|
|
5950
|
+
};
|
|
4818
5951
|
const snapshot = {
|
|
4819
5952
|
application,
|
|
4820
5953
|
graph: app.graph,
|
|
4821
5954
|
signals,
|
|
4822
5955
|
performance,
|
|
5956
|
+
components,
|
|
5957
|
+
overlays: interactions.overlays,
|
|
5958
|
+
transitions: interactions.transitions,
|
|
5959
|
+
diagnostics,
|
|
4823
5960
|
...sources.router !== void 0 ? { router: inspectRouter(sources.router) } : {},
|
|
4824
5961
|
...sources.resources !== void 0 ? { resources: mapInspect(sources.resources, (r) => inspectResource(r)) } : {},
|
|
4825
5962
|
...sources.forms !== void 0 ? { forms: mapInspect(sources.forms, (f) => inspectForm(f)) } : {},
|
|
@@ -4860,6 +5997,25 @@ function formatSnapshot(s) {
|
|
|
4860
5997
|
for (const [label, sig] of Object.entries(s.signals.live)) {
|
|
4861
5998
|
lines.push(` ${label} [${sig.kind}] = ${format(sig.value)} \xB7 observers ${sig.observerCount ?? "?"}`);
|
|
4862
5999
|
}
|
|
6000
|
+
if (s.components.length > 0) {
|
|
6001
|
+
lines.push(`Components: ${s.components.length}`);
|
|
6002
|
+
for (const c of s.components) {
|
|
6003
|
+
lines.push(` ${" ".repeat(c.depth)}${c.name}${c.key !== void 0 ? ` (#${c.key})` : ""} \xB7 children ${c.childCount}`);
|
|
6004
|
+
}
|
|
6005
|
+
}
|
|
6006
|
+
if (s.overlays.length > 0) {
|
|
6007
|
+
lines.push(`Overlays: ${s.overlays.length}`);
|
|
6008
|
+
for (const o of s.overlays) {
|
|
6009
|
+
const kind = o.modal ? "modal" : o.menu ? "menu" : o.takesFocus ? "focusable" : "non-modal";
|
|
6010
|
+
lines.push(` ${o.key ?? o.id} [${kind}] ${o.open ? "open" : "closed"}`);
|
|
6011
|
+
}
|
|
6012
|
+
}
|
|
6013
|
+
if (s.transitions.length > 0) {
|
|
6014
|
+
lines.push(`Transitions: ${s.transitions.length}`);
|
|
6015
|
+
for (const t of s.transitions) {
|
|
6016
|
+
lines.push(` ${t.key ?? t.id} on <${t.nodeType}> \xB7 ${t.duration}ms${t.appear ? " \xB7 appear" : ""}`);
|
|
6017
|
+
}
|
|
6018
|
+
}
|
|
4863
6019
|
if (s.router !== void 0) {
|
|
4864
6020
|
lines.push(`Router: ${s.router.path} (${s.router.pattern})${s.router.isFallback ? " [fallback]" : ""}`);
|
|
4865
6021
|
}
|
|
@@ -4893,6 +6049,12 @@ function formatSnapshot(s) {
|
|
|
4893
6049
|
for (const d of s.performance.diagnostics) {
|
|
4894
6050
|
lines.push(` ${d.code}: ${d.message}`);
|
|
4895
6051
|
}
|
|
6052
|
+
lines.push(
|
|
6053
|
+
`Diagnostics: ${s.diagnostics.errors} error(s), ${s.diagnostics.warnings} warning(s)`
|
|
6054
|
+
);
|
|
6055
|
+
for (const m of s.diagnostics.messages) {
|
|
6056
|
+
lines.push(` ${m}`);
|
|
6057
|
+
}
|
|
4896
6058
|
return lines.join("\n");
|
|
4897
6059
|
}
|
|
4898
6060
|
function format(value) {
|
|
@@ -4908,6 +6070,176 @@ function format(value) {
|
|
|
4908
6070
|
return String(value);
|
|
4909
6071
|
}
|
|
4910
6072
|
|
|
6073
|
+
// ../devtools/src/view.ts
|
|
6074
|
+
function escapeHtml(value) {
|
|
6075
|
+
const s = typeof value === "string" ? value : stringifyValue(value);
|
|
6076
|
+
return s.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """).replace(/'/g, "'");
|
|
6077
|
+
}
|
|
6078
|
+
function stringifyValue(value) {
|
|
6079
|
+
if (value === null || value === void 0) return String(value);
|
|
6080
|
+
if (typeof value === "object") {
|
|
6081
|
+
try {
|
|
6082
|
+
return JSON.stringify(value);
|
|
6083
|
+
} catch {
|
|
6084
|
+
return "[object]";
|
|
6085
|
+
}
|
|
6086
|
+
}
|
|
6087
|
+
return String(value);
|
|
6088
|
+
}
|
|
6089
|
+
function section(title, count, body) {
|
|
6090
|
+
const badge = count === void 0 ? "" : ` <span class="st-count">${count}</span>`;
|
|
6091
|
+
return `<section class="st-panel"><h2>${escapeHtml(title)}${badge}</h2>${body}</section>`;
|
|
6092
|
+
}
|
|
6093
|
+
function ul(items) {
|
|
6094
|
+
if (items.length === 0) return '<p class="st-empty">(none)</p>';
|
|
6095
|
+
return `<ul>${items.map((i) => `<li>${i}</li>`).join("")}</ul>`;
|
|
6096
|
+
}
|
|
6097
|
+
function renderDevToolsHTML(s) {
|
|
6098
|
+
const app = s.application;
|
|
6099
|
+
const parts = [];
|
|
6100
|
+
parts.push(
|
|
6101
|
+
section(
|
|
6102
|
+
"Application",
|
|
6103
|
+
void 0,
|
|
6104
|
+
`<p>${escapeHtml(app.identity.name)} <span class="st-dim">v${escapeHtml(app.identity.version)}</span></p><p class="st-dim">${app.nodeCount} nodes \xB7 depth ${app.maxDepth} \xB7 ${app.pages.length} page(s) \xB7 ${app.signalCount} signals \xB7 ${app.eventHandlers} handlers \xB7 ${app.stateBindings} bindings</p>`
|
|
6105
|
+
)
|
|
6106
|
+
);
|
|
6107
|
+
parts.push(
|
|
6108
|
+
section(
|
|
6109
|
+
"Components",
|
|
6110
|
+
s.components.length,
|
|
6111
|
+
ul(
|
|
6112
|
+
s.components.map(
|
|
6113
|
+
(c) => `<span class="st-depth" style="--d:${c.depth}"></span><code>${escapeHtml(c.name)}</code>` + (c.key !== void 0 ? ` <span class="st-key">#${escapeHtml(c.key)}</span>` : "") + ` <span class="st-dim">${c.childCount} child(ren)</span>`
|
|
6114
|
+
)
|
|
6115
|
+
)
|
|
6116
|
+
)
|
|
6117
|
+
);
|
|
6118
|
+
parts.push(section("Graph", void 0, `<pre class="st-tree">${escapeHtml(renderNodeTree(s.graph))}</pre>`));
|
|
6119
|
+
parts.push(
|
|
6120
|
+
section(
|
|
6121
|
+
"Signals",
|
|
6122
|
+
s.signals.boundSignalIds.length,
|
|
6123
|
+
`<p class="st-dim">${s.signals.boundSignalIds.length} bound in graph \xB7 effects shown as observer counts (no global effect registry)</p>` + ul(
|
|
6124
|
+
Object.entries(s.signals.live).map(
|
|
6125
|
+
([label, sig]) => `<code>${escapeHtml(label)}</code> <span class="st-key">[${escapeHtml(sig.kind)}]</span> = <code>${escapeHtml(sig.value)}</code> <span class="st-dim">observers ${escapeHtml(sig.observerCount ?? "?")}</span>`
|
|
6126
|
+
)
|
|
6127
|
+
)
|
|
6128
|
+
)
|
|
6129
|
+
);
|
|
6130
|
+
if (s.router !== void 0) {
|
|
6131
|
+
parts.push(
|
|
6132
|
+
section(
|
|
6133
|
+
"Router",
|
|
6134
|
+
void 0,
|
|
6135
|
+
`<p><code>${escapeHtml(s.router.path)}</code> <span class="st-dim">(${escapeHtml(s.router.pattern)})${s.router.isFallback ? " \xB7 fallback" : ""}</span></p>`
|
|
6136
|
+
)
|
|
6137
|
+
);
|
|
6138
|
+
}
|
|
6139
|
+
if (s.resources !== void 0) {
|
|
6140
|
+
parts.push(
|
|
6141
|
+
section(
|
|
6142
|
+
"Resources",
|
|
6143
|
+
Object.keys(s.resources).length,
|
|
6144
|
+
ul(
|
|
6145
|
+
Object.entries(s.resources).map(
|
|
6146
|
+
([label, r]) => `<code>${escapeHtml(label)}</code>: ${escapeHtml(r.status)}` + (r.loading ? ' <span class="st-dim">(loading)</span>' : "") + (r.hasError ? ` <span class="st-err">!${escapeHtml(r.errorName)}</span>` : "")
|
|
6147
|
+
)
|
|
6148
|
+
)
|
|
6149
|
+
)
|
|
6150
|
+
);
|
|
6151
|
+
}
|
|
6152
|
+
parts.push(
|
|
6153
|
+
section(
|
|
6154
|
+
"Overlays",
|
|
6155
|
+
s.overlays.length,
|
|
6156
|
+
ul(
|
|
6157
|
+
s.overlays.map((o) => {
|
|
6158
|
+
const kind = o.modal ? "modal" : o.menu ? "menu" : o.takesFocus ? "focusable" : "non-modal";
|
|
6159
|
+
return `<code>${escapeHtml(o.key ?? o.id)}</code> <span class="st-key">[${kind}]</span> <span class="st-dim">${o.open ? "open" : "closed"}${o.closeOnEscape ? " \xB7 esc" : ""}${o.restoreFocus ? " \xB7 restore" : ""}</span>`;
|
|
6160
|
+
})
|
|
6161
|
+
)
|
|
6162
|
+
)
|
|
6163
|
+
);
|
|
6164
|
+
parts.push(
|
|
6165
|
+
section(
|
|
6166
|
+
"Transitions",
|
|
6167
|
+
s.transitions.length,
|
|
6168
|
+
ul(
|
|
6169
|
+
s.transitions.map(
|
|
6170
|
+
(t) => `<code>${escapeHtml(t.key ?? t.id)}</code> on <code><${escapeHtml(t.nodeType)}></code> <span class="st-dim">${t.duration}ms${t.appear ? " \xB7 appear" : ""}</span>`
|
|
6171
|
+
)
|
|
6172
|
+
)
|
|
6173
|
+
)
|
|
6174
|
+
);
|
|
6175
|
+
if (s.forms !== void 0) {
|
|
6176
|
+
parts.push(
|
|
6177
|
+
section(
|
|
6178
|
+
"Forms",
|
|
6179
|
+
Object.keys(s.forms).length,
|
|
6180
|
+
ul(
|
|
6181
|
+
Object.entries(s.forms).map(
|
|
6182
|
+
([label, f]) => `<code>${escapeHtml(label)}</code>: ${f.valid ? "valid" : "invalid"} \xB7 ${escapeHtml(f.status)} \xB7 ${f.fields.length} field(s)`
|
|
6183
|
+
)
|
|
6184
|
+
)
|
|
6185
|
+
)
|
|
6186
|
+
);
|
|
6187
|
+
}
|
|
6188
|
+
if (s.i18n !== void 0) {
|
|
6189
|
+
const missing = s.i18n.missingKeys;
|
|
6190
|
+
parts.push(
|
|
6191
|
+
section(
|
|
6192
|
+
"i18n",
|
|
6193
|
+
void 0,
|
|
6194
|
+
`<p><code>${escapeHtml(s.i18n.locale)}</code> of [${s.i18n.locales.map(escapeHtml).join(", ")}]${missing !== void 0 ? ` <span class="st-dim">\xB7 missing ${missing.length}</span>` : ""}</p>`
|
|
6195
|
+
)
|
|
6196
|
+
);
|
|
6197
|
+
}
|
|
6198
|
+
parts.push(
|
|
6199
|
+
section(
|
|
6200
|
+
"Performance",
|
|
6201
|
+
s.performance.diagnostics.length,
|
|
6202
|
+
`<p class="st-dim">Structural counts, not runtime timings \u2014 not a production profiler.</p>` + ul(s.performance.diagnostics.map((d) => `<code>${escapeHtml(d.code)}</code>: ${escapeHtml(d.message)}`))
|
|
6203
|
+
)
|
|
6204
|
+
);
|
|
6205
|
+
parts.push(
|
|
6206
|
+
section(
|
|
6207
|
+
"Diagnostics",
|
|
6208
|
+
s.diagnostics.errors + s.diagnostics.warnings,
|
|
6209
|
+
`<p class="st-dim">${s.diagnostics.errors} error(s) \xB7 ${s.diagnostics.warnings} warning(s)</p>` + ul(s.diagnostics.messages.map((m) => escapeHtml(m)))
|
|
6210
|
+
)
|
|
6211
|
+
);
|
|
6212
|
+
const title = `StreetUI DevTools \u2014 ${escapeHtml(app.identity.name)}`;
|
|
6213
|
+
return `<!doctype html><html lang="en"><head><meta charset="utf-8"><title>${title}</title><style>${DEVTOOLS_CSS}</style></head><body class="st-devtools"><header class="st-header"><h1>${title} <span class="st-dim">v${escapeHtml(app.identity.version)}</span></h1></header><main>${parts.join("")}</main></body></html>`;
|
|
6214
|
+
}
|
|
6215
|
+
function renderNodeTree(node) {
|
|
6216
|
+
const lines = [];
|
|
6217
|
+
const walk = (n) => {
|
|
6218
|
+
const indent = " ".repeat(n.depth);
|
|
6219
|
+
const key = n.key !== void 0 ? ` #${n.key}` : "";
|
|
6220
|
+
lines.push(`${indent}<${n.type}${key}> ${n.id}`);
|
|
6221
|
+
for (const c of n.children) walk(c);
|
|
6222
|
+
};
|
|
6223
|
+
walk(node);
|
|
6224
|
+
return lines.join("\n");
|
|
6225
|
+
}
|
|
6226
|
+
var DEVTOOLS_CSS = [
|
|
6227
|
+
".st-devtools{font:13px/1.5 ui-monospace,SFMono-Regular,Menlo,monospace;margin:0;color:#e6e6e6;background:#1e1e28}",
|
|
6228
|
+
".st-header{padding:12px 16px;border-bottom:1px solid #333;background:#15151c}",
|
|
6229
|
+
".st-header h1{font-size:14px;margin:0}",
|
|
6230
|
+
"main{padding:8px 16px}",
|
|
6231
|
+
".st-panel{margin:12px 0;border:1px solid #2c2c38;border-radius:6px;overflow:hidden}",
|
|
6232
|
+
".st-panel h2{font-size:12px;text-transform:uppercase;letter-spacing:.04em;margin:0;padding:6px 10px;background:#23232e}",
|
|
6233
|
+
".st-panel ul{list-style:none;margin:0;padding:6px 10px}",
|
|
6234
|
+
".st-panel li{padding:1px 0}",
|
|
6235
|
+
".st-panel p{margin:6px 10px}",
|
|
6236
|
+
".st-count{background:#3a3a4a;border-radius:10px;padding:0 7px;font-size:11px;float:right}",
|
|
6237
|
+
".st-dim{color:#8a8a9a}.st-key{color:#7db4ff}.st-err{color:#ff8a8a}.st-empty{color:#6a6a7a}",
|
|
6238
|
+
".st-tree{margin:6px 10px;white-space:pre;overflow:auto;color:#c8c8d4}",
|
|
6239
|
+
".st-depth{display:inline-block}.st-depth{width:calc(var(--d,0)*12px)}",
|
|
6240
|
+
"code{color:#d7d7e0}"
|
|
6241
|
+
].join("");
|
|
6242
|
+
|
|
4911
6243
|
// src/config.ts
|
|
4912
6244
|
function defineConfig(config) {
|
|
4913
6245
|
return config;
|
|
@@ -4931,6 +6263,8 @@ function defineConfig(config) {
|
|
|
4931
6263
|
FOCUSABLE_SELECTOR,
|
|
4932
6264
|
FormBuilderImpl,
|
|
4933
6265
|
GraphNode,
|
|
6266
|
+
HeadManager,
|
|
6267
|
+
HttpError,
|
|
4934
6268
|
Lifecycle,
|
|
4935
6269
|
ListBuilderImpl,
|
|
4936
6270
|
NodeInstance,
|
|
@@ -4954,6 +6288,7 @@ function defineConfig(config) {
|
|
|
4954
6288
|
StreetFrameworkError,
|
|
4955
6289
|
StreetRenderHandle,
|
|
4956
6290
|
StreetRendererImpl,
|
|
6291
|
+
TransitionController,
|
|
4957
6292
|
VERSION,
|
|
4958
6293
|
a11yIds,
|
|
4959
6294
|
applyNodeProps,
|
|
@@ -4968,8 +6303,11 @@ function defineConfig(config) {
|
|
|
4968
6303
|
consoleDiagnosticSink,
|
|
4969
6304
|
consoleHydrationDiagnosticSink,
|
|
4970
6305
|
containFocus,
|
|
6306
|
+
createAnnouncer,
|
|
4971
6307
|
createApplication,
|
|
6308
|
+
createAuthSession,
|
|
4972
6309
|
createBrowserHistory,
|
|
6310
|
+
createClient,
|
|
4973
6311
|
createContext,
|
|
4974
6312
|
createDevTools,
|
|
4975
6313
|
createForm,
|
|
@@ -4985,10 +6323,12 @@ function defineConfig(config) {
|
|
|
4985
6323
|
createStreetEvent,
|
|
4986
6324
|
defineConfig,
|
|
4987
6325
|
derived,
|
|
6326
|
+
describeError,
|
|
4988
6327
|
diagnosePerformance,
|
|
4989
6328
|
effect,
|
|
4990
6329
|
email,
|
|
4991
6330
|
environment,
|
|
6331
|
+
escapeHtml,
|
|
4992
6332
|
escapeHtmlAttr,
|
|
4993
6333
|
escapeHtmlText,
|
|
4994
6334
|
flushSync,
|
|
@@ -5002,6 +6342,7 @@ function defineConfig(config) {
|
|
|
5002
6342
|
generateApplicationId,
|
|
5003
6343
|
generateNodeId,
|
|
5004
6344
|
getFocusable,
|
|
6345
|
+
getResolvedTransition,
|
|
5005
6346
|
globalEventBus,
|
|
5006
6347
|
headingUpdate,
|
|
5007
6348
|
hydrateGraph,
|
|
@@ -5012,12 +6353,16 @@ function defineConfig(config) {
|
|
|
5012
6353
|
inspectForm,
|
|
5013
6354
|
inspectGraph,
|
|
5014
6355
|
inspectI18n,
|
|
6356
|
+
inspectInteractions,
|
|
5015
6357
|
inspectResource,
|
|
5016
6358
|
inspectRouter,
|
|
5017
6359
|
inspectSignal,
|
|
5018
6360
|
interpolate,
|
|
5019
6361
|
isBatching,
|
|
5020
6362
|
isComponentDefinition,
|
|
6363
|
+
isHeadContribution,
|
|
6364
|
+
isTransitionConfig,
|
|
6365
|
+
linkUpdate,
|
|
5021
6366
|
matchPattern,
|
|
5022
6367
|
matchRoutes,
|
|
5023
6368
|
maxLength,
|
|
@@ -5025,6 +6370,7 @@ function defineConfig(config) {
|
|
|
5025
6370
|
mountGraph,
|
|
5026
6371
|
mountNode,
|
|
5027
6372
|
mountRouter,
|
|
6373
|
+
mutation,
|
|
5028
6374
|
nextId,
|
|
5029
6375
|
nodeIdPrefix,
|
|
5030
6376
|
nodeTypeStats,
|
|
@@ -5041,14 +6387,21 @@ function defineConfig(config) {
|
|
|
5041
6387
|
readState,
|
|
5042
6388
|
reconcileChildren,
|
|
5043
6389
|
reconcileChildrenByPlan,
|
|
6390
|
+
renderDevToolsHTML,
|
|
6391
|
+
renderHead,
|
|
5044
6392
|
renderToString,
|
|
5045
6393
|
reportDiagnostic,
|
|
6394
|
+
reportError,
|
|
5046
6395
|
required,
|
|
5047
6396
|
resetIdCounter,
|
|
6397
|
+
resolveHead,
|
|
5048
6398
|
resolveTag,
|
|
6399
|
+
resolveTransition,
|
|
5049
6400
|
resource,
|
|
5050
6401
|
restoreFocus,
|
|
5051
6402
|
routerOutlet,
|
|
6403
|
+
rovingMenu,
|
|
6404
|
+
runElementTransition,
|
|
5052
6405
|
runValidators,
|
|
5053
6406
|
saveFocus,
|
|
5054
6407
|
scheduleImmediate,
|
|
@@ -5069,6 +6422,7 @@ function defineConfig(config) {
|
|
|
5069
6422
|
validateGraph,
|
|
5070
6423
|
wireComponentBehavior,
|
|
5071
6424
|
wireEvents,
|
|
6425
|
+
wireHeadBehavior,
|
|
5072
6426
|
wireOverlayBehavior,
|
|
5073
6427
|
wireReactiveList,
|
|
5074
6428
|
wireSignalBindings
|