@tanstack/router-core 1.132.0-alpha.1 → 1.132.0-alpha.3
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/cjs/Matches.cjs.map +1 -1
- package/dist/cjs/Matches.d.cts +7 -9
- package/dist/cjs/index.cjs +8 -2
- package/dist/cjs/index.cjs.map +1 -1
- package/dist/cjs/index.d.cts +6 -2
- package/dist/cjs/load-matches.cjs +636 -0
- package/dist/cjs/load-matches.cjs.map +1 -0
- package/dist/cjs/load-matches.d.cts +16 -0
- package/dist/cjs/qss.cjs +19 -19
- package/dist/cjs/qss.cjs.map +1 -1
- package/dist/cjs/qss.d.cts +6 -4
- package/dist/cjs/redirect.cjs +3 -3
- package/dist/cjs/redirect.cjs.map +1 -1
- package/dist/cjs/route.cjs.map +1 -1
- package/dist/cjs/route.d.cts +0 -4
- package/dist/cjs/router.cjs +64 -632
- package/dist/cjs/router.cjs.map +1 -1
- package/dist/cjs/router.d.cts +14 -26
- package/dist/cjs/scroll-restoration.cjs +20 -25
- package/dist/cjs/scroll-restoration.cjs.map +1 -1
- package/dist/cjs/scroll-restoration.d.cts +0 -9
- package/dist/cjs/searchParams.cjs +7 -15
- package/dist/cjs/searchParams.cjs.map +1 -1
- package/dist/cjs/ssr/constants.cjs +5 -0
- package/dist/cjs/ssr/constants.cjs.map +1 -0
- package/dist/cjs/ssr/constants.d.cts +1 -0
- package/dist/cjs/ssr/{seroval-plugins.cjs → serializer/ShallowErrorPlugin.cjs} +2 -2
- package/dist/cjs/ssr/serializer/ShallowErrorPlugin.cjs.map +1 -0
- package/dist/cjs/ssr/{seroval-plugins.d.cts → serializer/ShallowErrorPlugin.d.cts} +1 -2
- package/dist/cjs/ssr/serializer/seroval-plugins.cjs +11 -0
- package/dist/cjs/ssr/serializer/seroval-plugins.cjs.map +1 -0
- package/dist/cjs/ssr/serializer/seroval-plugins.d.cts +2 -0
- package/dist/cjs/ssr/serializer/transformer.cjs +50 -0
- package/dist/cjs/ssr/serializer/transformer.cjs.map +1 -0
- package/dist/cjs/ssr/serializer/transformer.d.cts +18 -0
- package/dist/cjs/ssr/ssr-client.cjs +53 -40
- package/dist/cjs/ssr/ssr-client.cjs.map +1 -1
- package/dist/cjs/ssr/ssr-client.d.cts +5 -1
- package/dist/cjs/ssr/ssr-server.cjs +12 -10
- package/dist/cjs/ssr/ssr-server.cjs.map +1 -1
- package/dist/cjs/ssr/ssr-server.d.cts +0 -1
- package/dist/cjs/ssr/tsrScript.cjs +1 -1
- package/dist/cjs/ssr/tsrScript.cjs.map +1 -1
- package/dist/cjs/typePrimitives.d.cts +6 -6
- package/dist/cjs/utils.cjs +14 -7
- package/dist/cjs/utils.cjs.map +1 -1
- package/dist/cjs/utils.d.cts +2 -1
- package/dist/esm/Matches.d.ts +7 -9
- package/dist/esm/Matches.js.map +1 -1
- package/dist/esm/index.d.ts +6 -2
- package/dist/esm/index.js +9 -3
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/load-matches.d.ts +16 -0
- package/dist/esm/load-matches.js +636 -0
- package/dist/esm/load-matches.js.map +1 -0
- package/dist/esm/qss.d.ts +6 -4
- package/dist/esm/qss.js +19 -19
- package/dist/esm/qss.js.map +1 -1
- package/dist/esm/redirect.js +3 -3
- package/dist/esm/redirect.js.map +1 -1
- package/dist/esm/route.d.ts +0 -4
- package/dist/esm/route.js.map +1 -1
- package/dist/esm/router.d.ts +14 -26
- package/dist/esm/router.js +64 -632
- package/dist/esm/router.js.map +1 -1
- package/dist/esm/scroll-restoration.d.ts +0 -9
- package/dist/esm/scroll-restoration.js +20 -25
- package/dist/esm/scroll-restoration.js.map +1 -1
- package/dist/esm/searchParams.js +7 -15
- package/dist/esm/searchParams.js.map +1 -1
- package/dist/esm/ssr/constants.d.ts +1 -0
- package/dist/esm/ssr/constants.js +5 -0
- package/dist/esm/ssr/constants.js.map +1 -0
- package/dist/esm/ssr/{seroval-plugins.d.ts → serializer/ShallowErrorPlugin.d.ts} +1 -2
- package/dist/esm/ssr/{seroval-plugins.js → serializer/ShallowErrorPlugin.js} +2 -2
- package/dist/esm/ssr/serializer/ShallowErrorPlugin.js.map +1 -0
- package/dist/esm/ssr/serializer/seroval-plugins.d.ts +2 -0
- package/dist/esm/ssr/serializer/seroval-plugins.js +11 -0
- package/dist/esm/ssr/serializer/seroval-plugins.js.map +1 -0
- package/dist/esm/ssr/serializer/transformer.d.ts +18 -0
- package/dist/esm/ssr/serializer/transformer.js +50 -0
- package/dist/esm/ssr/serializer/transformer.js.map +1 -0
- package/dist/esm/ssr/ssr-client.d.ts +5 -1
- package/dist/esm/ssr/ssr-client.js +53 -40
- package/dist/esm/ssr/ssr-client.js.map +1 -1
- package/dist/esm/ssr/ssr-server.d.ts +0 -1
- package/dist/esm/ssr/ssr-server.js +12 -10
- package/dist/esm/ssr/ssr-server.js.map +1 -1
- package/dist/esm/ssr/tsrScript.js +1 -1
- package/dist/esm/ssr/tsrScript.js.map +1 -1
- package/dist/esm/typePrimitives.d.ts +6 -6
- package/dist/esm/utils.d.ts +2 -1
- package/dist/esm/utils.js +14 -7
- package/dist/esm/utils.js.map +1 -1
- package/package.json +1 -1
- package/src/Matches.ts +16 -8
- package/src/index.ts +12 -2
- package/src/load-matches.ts +955 -0
- package/src/qss.ts +27 -24
- package/src/redirect.ts +3 -3
- package/src/route.ts +10 -2
- package/src/router.ts +99 -893
- package/src/scroll-restoration.ts +25 -32
- package/src/searchParams.ts +8 -19
- package/src/ssr/constants.ts +1 -0
- package/src/ssr/{seroval-plugins.ts → serializer/ShallowErrorPlugin.ts} +2 -2
- package/src/ssr/serializer/seroval-plugins.ts +9 -0
- package/src/ssr/serializer/transformer.ts +78 -0
- package/src/ssr/ssr-client.ts +72 -44
- package/src/ssr/ssr-server.ts +18 -10
- package/src/ssr/tsrScript.ts +5 -1
- package/src/typePrimitives.ts +6 -6
- package/src/utils.ts +21 -10
- package/dist/cjs/ssr/seroval-plugins.cjs.map +0 -1
- package/dist/esm/ssr/seroval-plugins.js.map +0 -1
|
@@ -0,0 +1,636 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
3
|
+
const store = require("@tanstack/store");
|
|
4
|
+
const invariant = require("tiny-invariant");
|
|
5
|
+
const utils = require("./utils.cjs");
|
|
6
|
+
const notFound = require("./not-found.cjs");
|
|
7
|
+
const root = require("./root.cjs");
|
|
8
|
+
const redirect = require("./redirect.cjs");
|
|
9
|
+
const triggerOnReady = (inner) => {
|
|
10
|
+
if (!inner.rendered) {
|
|
11
|
+
inner.rendered = true;
|
|
12
|
+
return inner.onReady?.();
|
|
13
|
+
}
|
|
14
|
+
};
|
|
15
|
+
const resolvePreload = (inner, matchId) => {
|
|
16
|
+
return !!(inner.preload && !inner.router.state.matches.some((d) => d.id === matchId));
|
|
17
|
+
};
|
|
18
|
+
const _handleNotFound = (inner, err) => {
|
|
19
|
+
const routeCursor = inner.router.routesById[err.routeId ?? ""] ?? inner.router.routeTree;
|
|
20
|
+
if (!routeCursor.options.notFoundComponent && inner.router.options?.defaultNotFoundComponent) {
|
|
21
|
+
routeCursor.options.notFoundComponent = inner.router.options.defaultNotFoundComponent;
|
|
22
|
+
}
|
|
23
|
+
invariant(
|
|
24
|
+
routeCursor.options.notFoundComponent,
|
|
25
|
+
"No notFoundComponent found. Please set a notFoundComponent on your route or provide a defaultNotFoundComponent to the router."
|
|
26
|
+
);
|
|
27
|
+
const matchForRoute = inner.matches.find((m) => m.routeId === routeCursor.id);
|
|
28
|
+
invariant(matchForRoute, "Could not find match for route: " + routeCursor.id);
|
|
29
|
+
inner.updateMatch(matchForRoute.id, (prev) => ({
|
|
30
|
+
...prev,
|
|
31
|
+
status: "notFound",
|
|
32
|
+
error: err,
|
|
33
|
+
isFetching: false
|
|
34
|
+
}));
|
|
35
|
+
if (err.routerCode === "BEFORE_LOAD" && routeCursor.parentRoute) {
|
|
36
|
+
err.routeId = routeCursor.parentRoute.id;
|
|
37
|
+
_handleNotFound(inner, err);
|
|
38
|
+
}
|
|
39
|
+
};
|
|
40
|
+
const handleRedirectAndNotFound = (inner, match, err) => {
|
|
41
|
+
if (!redirect.isRedirect(err) && !notFound.isNotFound(err)) return;
|
|
42
|
+
if (redirect.isRedirect(err) && err.redirectHandled && !err.options.reloadDocument) {
|
|
43
|
+
throw err;
|
|
44
|
+
}
|
|
45
|
+
if (match) {
|
|
46
|
+
match._nonReactive.beforeLoadPromise?.resolve();
|
|
47
|
+
match._nonReactive.loaderPromise?.resolve();
|
|
48
|
+
match._nonReactive.beforeLoadPromise = void 0;
|
|
49
|
+
match._nonReactive.loaderPromise = void 0;
|
|
50
|
+
const status = redirect.isRedirect(err) ? "redirected" : "notFound";
|
|
51
|
+
inner.updateMatch(match.id, (prev) => ({
|
|
52
|
+
...prev,
|
|
53
|
+
status,
|
|
54
|
+
isFetching: false,
|
|
55
|
+
error: err
|
|
56
|
+
}));
|
|
57
|
+
if (notFound.isNotFound(err) && !err.routeId) {
|
|
58
|
+
err.routeId = match.routeId;
|
|
59
|
+
}
|
|
60
|
+
match._nonReactive.loadPromise?.resolve();
|
|
61
|
+
}
|
|
62
|
+
if (redirect.isRedirect(err)) {
|
|
63
|
+
inner.rendered = true;
|
|
64
|
+
err.options._fromLocation = inner.location;
|
|
65
|
+
err.redirectHandled = true;
|
|
66
|
+
err = inner.router.resolveRedirect(err);
|
|
67
|
+
throw err;
|
|
68
|
+
} else {
|
|
69
|
+
_handleNotFound(inner, err);
|
|
70
|
+
throw err;
|
|
71
|
+
}
|
|
72
|
+
};
|
|
73
|
+
const shouldSkipLoader = (inner, matchId) => {
|
|
74
|
+
const match = inner.router.getMatch(matchId);
|
|
75
|
+
if (!inner.router.isServer && match._nonReactive.dehydrated) {
|
|
76
|
+
return true;
|
|
77
|
+
}
|
|
78
|
+
if (inner.router.isServer && match.ssr === false) {
|
|
79
|
+
return true;
|
|
80
|
+
}
|
|
81
|
+
return false;
|
|
82
|
+
};
|
|
83
|
+
const handleSerialError = (inner, index, err, routerCode) => {
|
|
84
|
+
const { id: matchId, routeId } = inner.matches[index];
|
|
85
|
+
const route = inner.router.looseRoutesById[routeId];
|
|
86
|
+
if (err instanceof Promise) {
|
|
87
|
+
throw err;
|
|
88
|
+
}
|
|
89
|
+
err.routerCode = routerCode;
|
|
90
|
+
inner.firstBadMatchIndex ??= index;
|
|
91
|
+
handleRedirectAndNotFound(inner, inner.router.getMatch(matchId), err);
|
|
92
|
+
try {
|
|
93
|
+
route.options.onError?.(err);
|
|
94
|
+
} catch (errorHandlerErr) {
|
|
95
|
+
err = errorHandlerErr;
|
|
96
|
+
handleRedirectAndNotFound(inner, inner.router.getMatch(matchId), err);
|
|
97
|
+
}
|
|
98
|
+
inner.updateMatch(matchId, (prev) => {
|
|
99
|
+
prev._nonReactive.beforeLoadPromise?.resolve();
|
|
100
|
+
prev._nonReactive.beforeLoadPromise = void 0;
|
|
101
|
+
prev._nonReactive.loadPromise?.resolve();
|
|
102
|
+
return {
|
|
103
|
+
...prev,
|
|
104
|
+
error: err,
|
|
105
|
+
status: "error",
|
|
106
|
+
isFetching: false,
|
|
107
|
+
updatedAt: Date.now(),
|
|
108
|
+
abortController: new AbortController()
|
|
109
|
+
};
|
|
110
|
+
});
|
|
111
|
+
};
|
|
112
|
+
const isBeforeLoadSsr = (inner, matchId, index, route) => {
|
|
113
|
+
const existingMatch = inner.router.getMatch(matchId);
|
|
114
|
+
const parentMatchId = inner.matches[index - 1]?.id;
|
|
115
|
+
const parentMatch = parentMatchId ? inner.router.getMatch(parentMatchId) : void 0;
|
|
116
|
+
if (inner.router.isShell()) {
|
|
117
|
+
existingMatch.ssr = matchId === root.rootRouteId;
|
|
118
|
+
return;
|
|
119
|
+
}
|
|
120
|
+
if (parentMatch?.ssr === false) {
|
|
121
|
+
existingMatch.ssr = false;
|
|
122
|
+
return;
|
|
123
|
+
}
|
|
124
|
+
const parentOverride = (tempSsr2) => {
|
|
125
|
+
if (tempSsr2 === true && parentMatch?.ssr === "data-only") {
|
|
126
|
+
return "data-only";
|
|
127
|
+
}
|
|
128
|
+
return tempSsr2;
|
|
129
|
+
};
|
|
130
|
+
const defaultSsr = inner.router.options.defaultSsr ?? true;
|
|
131
|
+
if (route.options.ssr === void 0) {
|
|
132
|
+
existingMatch.ssr = parentOverride(defaultSsr);
|
|
133
|
+
return;
|
|
134
|
+
}
|
|
135
|
+
if (typeof route.options.ssr !== "function") {
|
|
136
|
+
existingMatch.ssr = parentOverride(route.options.ssr);
|
|
137
|
+
return;
|
|
138
|
+
}
|
|
139
|
+
const { search, params } = existingMatch;
|
|
140
|
+
const ssrFnContext = {
|
|
141
|
+
search: makeMaybe(search, existingMatch.searchError),
|
|
142
|
+
params: makeMaybe(params, existingMatch.paramsError),
|
|
143
|
+
location: inner.location,
|
|
144
|
+
matches: inner.matches.map((match) => ({
|
|
145
|
+
index: match.index,
|
|
146
|
+
pathname: match.pathname,
|
|
147
|
+
fullPath: match.fullPath,
|
|
148
|
+
staticData: match.staticData,
|
|
149
|
+
id: match.id,
|
|
150
|
+
routeId: match.routeId,
|
|
151
|
+
search: makeMaybe(match.search, match.searchError),
|
|
152
|
+
params: makeMaybe(match.params, match.paramsError),
|
|
153
|
+
ssr: match.ssr
|
|
154
|
+
}))
|
|
155
|
+
};
|
|
156
|
+
const tempSsr = route.options.ssr(ssrFnContext);
|
|
157
|
+
if (utils.isPromise(tempSsr)) {
|
|
158
|
+
return tempSsr.then((ssr) => {
|
|
159
|
+
existingMatch.ssr = parentOverride(ssr ?? defaultSsr);
|
|
160
|
+
});
|
|
161
|
+
}
|
|
162
|
+
existingMatch.ssr = parentOverride(tempSsr ?? defaultSsr);
|
|
163
|
+
return;
|
|
164
|
+
};
|
|
165
|
+
const setupPendingTimeout = (inner, matchId, route, match) => {
|
|
166
|
+
if (match._nonReactive.pendingTimeout !== void 0) return;
|
|
167
|
+
const pendingMs = route.options.pendingMs ?? inner.router.options.defaultPendingMs;
|
|
168
|
+
const shouldPending = !!(inner.onReady && !inner.router.isServer && !resolvePreload(inner, matchId) && (route.options.loader || route.options.beforeLoad || routeNeedsPreload(route)) && typeof pendingMs === "number" && pendingMs !== Infinity && (route.options.pendingComponent ?? inner.router.options?.defaultPendingComponent));
|
|
169
|
+
if (shouldPending) {
|
|
170
|
+
const pendingTimeout = setTimeout(() => {
|
|
171
|
+
triggerOnReady(inner);
|
|
172
|
+
}, pendingMs);
|
|
173
|
+
match._nonReactive.pendingTimeout = pendingTimeout;
|
|
174
|
+
}
|
|
175
|
+
};
|
|
176
|
+
const preBeforeLoadSetup = (inner, matchId, route) => {
|
|
177
|
+
const existingMatch = inner.router.getMatch(matchId);
|
|
178
|
+
if (!existingMatch._nonReactive.beforeLoadPromise && !existingMatch._nonReactive.loaderPromise)
|
|
179
|
+
return;
|
|
180
|
+
setupPendingTimeout(inner, matchId, route, existingMatch);
|
|
181
|
+
const then = () => {
|
|
182
|
+
const match = inner.router.getMatch(matchId);
|
|
183
|
+
if (match.preload && (match.status === "redirected" || match.status === "notFound")) {
|
|
184
|
+
handleRedirectAndNotFound(inner, match, match.error);
|
|
185
|
+
}
|
|
186
|
+
};
|
|
187
|
+
return existingMatch._nonReactive.beforeLoadPromise ? existingMatch._nonReactive.beforeLoadPromise.then(then) : then();
|
|
188
|
+
};
|
|
189
|
+
const executeBeforeLoad = (inner, matchId, index, route) => {
|
|
190
|
+
const match = inner.router.getMatch(matchId);
|
|
191
|
+
const prevLoadPromise = match._nonReactive.loadPromise;
|
|
192
|
+
match._nonReactive.loadPromise = utils.createControlledPromise(() => {
|
|
193
|
+
prevLoadPromise?.resolve();
|
|
194
|
+
});
|
|
195
|
+
const { paramsError, searchError } = match;
|
|
196
|
+
if (paramsError) {
|
|
197
|
+
handleSerialError(inner, index, paramsError, "PARSE_PARAMS");
|
|
198
|
+
}
|
|
199
|
+
if (searchError) {
|
|
200
|
+
handleSerialError(inner, index, searchError, "VALIDATE_SEARCH");
|
|
201
|
+
}
|
|
202
|
+
setupPendingTimeout(inner, matchId, route, match);
|
|
203
|
+
const abortController = new AbortController();
|
|
204
|
+
const parentMatchId = inner.matches[index - 1]?.id;
|
|
205
|
+
const parentMatch = parentMatchId ? inner.router.getMatch(parentMatchId) : void 0;
|
|
206
|
+
const parentMatchContext = parentMatch?.context ?? inner.router.options.context ?? void 0;
|
|
207
|
+
const context = { ...parentMatchContext, ...match.__routeContext };
|
|
208
|
+
let isPending = false;
|
|
209
|
+
const pending = () => {
|
|
210
|
+
if (isPending) return;
|
|
211
|
+
isPending = true;
|
|
212
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
213
|
+
...prev,
|
|
214
|
+
isFetching: "beforeLoad",
|
|
215
|
+
fetchCount: prev.fetchCount + 1,
|
|
216
|
+
abortController,
|
|
217
|
+
context
|
|
218
|
+
}));
|
|
219
|
+
};
|
|
220
|
+
const resolve = () => {
|
|
221
|
+
match._nonReactive.beforeLoadPromise?.resolve();
|
|
222
|
+
match._nonReactive.beforeLoadPromise = void 0;
|
|
223
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
224
|
+
...prev,
|
|
225
|
+
isFetching: false
|
|
226
|
+
}));
|
|
227
|
+
};
|
|
228
|
+
if (!route.options.beforeLoad) {
|
|
229
|
+
store.batch(() => {
|
|
230
|
+
pending();
|
|
231
|
+
resolve();
|
|
232
|
+
});
|
|
233
|
+
return;
|
|
234
|
+
}
|
|
235
|
+
match._nonReactive.beforeLoadPromise = utils.createControlledPromise();
|
|
236
|
+
const { search, params, cause } = match;
|
|
237
|
+
const preload = resolvePreload(inner, matchId);
|
|
238
|
+
const beforeLoadFnContext = {
|
|
239
|
+
search,
|
|
240
|
+
abortController,
|
|
241
|
+
params,
|
|
242
|
+
preload,
|
|
243
|
+
context,
|
|
244
|
+
location: inner.location,
|
|
245
|
+
navigate: (opts) => inner.router.navigate({
|
|
246
|
+
...opts,
|
|
247
|
+
_fromLocation: inner.location
|
|
248
|
+
}),
|
|
249
|
+
buildLocation: inner.router.buildLocation,
|
|
250
|
+
cause: preload ? "preload" : cause,
|
|
251
|
+
matches: inner.matches
|
|
252
|
+
};
|
|
253
|
+
const updateContext = (beforeLoadContext2) => {
|
|
254
|
+
if (beforeLoadContext2 === void 0) {
|
|
255
|
+
store.batch(() => {
|
|
256
|
+
pending();
|
|
257
|
+
resolve();
|
|
258
|
+
});
|
|
259
|
+
return;
|
|
260
|
+
}
|
|
261
|
+
if (redirect.isRedirect(beforeLoadContext2) || notFound.isNotFound(beforeLoadContext2)) {
|
|
262
|
+
pending();
|
|
263
|
+
handleSerialError(inner, index, beforeLoadContext2, "BEFORE_LOAD");
|
|
264
|
+
}
|
|
265
|
+
store.batch(() => {
|
|
266
|
+
pending();
|
|
267
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
268
|
+
...prev,
|
|
269
|
+
__beforeLoadContext: beforeLoadContext2,
|
|
270
|
+
context: {
|
|
271
|
+
...prev.context,
|
|
272
|
+
...beforeLoadContext2
|
|
273
|
+
}
|
|
274
|
+
}));
|
|
275
|
+
resolve();
|
|
276
|
+
});
|
|
277
|
+
};
|
|
278
|
+
let beforeLoadContext;
|
|
279
|
+
try {
|
|
280
|
+
beforeLoadContext = route.options.beforeLoad(beforeLoadFnContext);
|
|
281
|
+
if (utils.isPromise(beforeLoadContext)) {
|
|
282
|
+
pending();
|
|
283
|
+
return beforeLoadContext.catch((err) => {
|
|
284
|
+
handleSerialError(inner, index, err, "BEFORE_LOAD");
|
|
285
|
+
}).then(updateContext);
|
|
286
|
+
}
|
|
287
|
+
} catch (err) {
|
|
288
|
+
pending();
|
|
289
|
+
handleSerialError(inner, index, err, "BEFORE_LOAD");
|
|
290
|
+
}
|
|
291
|
+
updateContext(beforeLoadContext);
|
|
292
|
+
return;
|
|
293
|
+
};
|
|
294
|
+
const handleBeforeLoad = (inner, index) => {
|
|
295
|
+
const { id: matchId, routeId } = inner.matches[index];
|
|
296
|
+
const route = inner.router.looseRoutesById[routeId];
|
|
297
|
+
const serverSsr = () => {
|
|
298
|
+
if (inner.router.isServer) {
|
|
299
|
+
const maybePromise = isBeforeLoadSsr(inner, matchId, index, route);
|
|
300
|
+
if (utils.isPromise(maybePromise)) return maybePromise.then(queueExecution);
|
|
301
|
+
}
|
|
302
|
+
return queueExecution();
|
|
303
|
+
};
|
|
304
|
+
const queueExecution = () => {
|
|
305
|
+
if (shouldSkipLoader(inner, matchId)) return;
|
|
306
|
+
const result = preBeforeLoadSetup(inner, matchId, route);
|
|
307
|
+
return utils.isPromise(result) ? result.then(execute) : execute();
|
|
308
|
+
};
|
|
309
|
+
const execute = () => executeBeforeLoad(inner, matchId, index, route);
|
|
310
|
+
return serverSsr();
|
|
311
|
+
};
|
|
312
|
+
const executeHead = (inner, matchId, route) => {
|
|
313
|
+
const match = inner.router.getMatch(matchId);
|
|
314
|
+
if (!match) {
|
|
315
|
+
return;
|
|
316
|
+
}
|
|
317
|
+
if (!route.options.head && !route.options.scripts && !route.options.headers) {
|
|
318
|
+
return;
|
|
319
|
+
}
|
|
320
|
+
const assetContext = {
|
|
321
|
+
matches: inner.matches,
|
|
322
|
+
match,
|
|
323
|
+
params: match.params,
|
|
324
|
+
loaderData: match.loaderData
|
|
325
|
+
};
|
|
326
|
+
return Promise.all([
|
|
327
|
+
route.options.head?.(assetContext),
|
|
328
|
+
route.options.scripts?.(assetContext),
|
|
329
|
+
route.options.headers?.(assetContext)
|
|
330
|
+
]).then(([headFnContent, scripts, headers]) => {
|
|
331
|
+
const meta = headFnContent?.meta;
|
|
332
|
+
const links = headFnContent?.links;
|
|
333
|
+
const headScripts = headFnContent?.scripts;
|
|
334
|
+
const styles = headFnContent?.styles;
|
|
335
|
+
return {
|
|
336
|
+
meta,
|
|
337
|
+
links,
|
|
338
|
+
headScripts,
|
|
339
|
+
headers,
|
|
340
|
+
scripts,
|
|
341
|
+
styles
|
|
342
|
+
};
|
|
343
|
+
});
|
|
344
|
+
};
|
|
345
|
+
const getLoaderContext = (inner, matchId, index, route) => {
|
|
346
|
+
const parentMatchPromise = inner.matchPromises[index - 1];
|
|
347
|
+
const { params, loaderDeps, abortController, context, cause } = inner.router.getMatch(matchId);
|
|
348
|
+
const preload = resolvePreload(inner, matchId);
|
|
349
|
+
return {
|
|
350
|
+
params,
|
|
351
|
+
deps: loaderDeps,
|
|
352
|
+
preload: !!preload,
|
|
353
|
+
parentMatchPromise,
|
|
354
|
+
abortController,
|
|
355
|
+
context,
|
|
356
|
+
location: inner.location,
|
|
357
|
+
navigate: (opts) => inner.router.navigate({
|
|
358
|
+
...opts,
|
|
359
|
+
_fromLocation: inner.location
|
|
360
|
+
}),
|
|
361
|
+
cause: preload ? "preload" : cause,
|
|
362
|
+
route
|
|
363
|
+
};
|
|
364
|
+
};
|
|
365
|
+
const runLoader = async (inner, matchId, index, route) => {
|
|
366
|
+
try {
|
|
367
|
+
const match = inner.router.getMatch(matchId);
|
|
368
|
+
try {
|
|
369
|
+
if (!inner.router.isServer || match.ssr === true) {
|
|
370
|
+
loadRouteChunk(route);
|
|
371
|
+
}
|
|
372
|
+
const loaderResult = route.options.loader?.(
|
|
373
|
+
getLoaderContext(inner, matchId, index, route)
|
|
374
|
+
);
|
|
375
|
+
const loaderResultIsPromise = route.options.loader && utils.isPromise(loaderResult);
|
|
376
|
+
const willLoadSomething = !!(loaderResultIsPromise || route._lazyPromise || route._componentsPromise || route.options.head || route.options.scripts || route.options.headers || match._nonReactive.minPendingPromise);
|
|
377
|
+
if (willLoadSomething) {
|
|
378
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
379
|
+
...prev,
|
|
380
|
+
isFetching: "loader"
|
|
381
|
+
}));
|
|
382
|
+
}
|
|
383
|
+
if (route.options.loader) {
|
|
384
|
+
const loaderData = loaderResultIsPromise ? await loaderResult : loaderResult;
|
|
385
|
+
handleRedirectAndNotFound(
|
|
386
|
+
inner,
|
|
387
|
+
inner.router.getMatch(matchId),
|
|
388
|
+
loaderData
|
|
389
|
+
);
|
|
390
|
+
if (loaderData !== void 0) {
|
|
391
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
392
|
+
...prev,
|
|
393
|
+
loaderData
|
|
394
|
+
}));
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
if (route._lazyPromise) await route._lazyPromise;
|
|
398
|
+
const headResult = executeHead(inner, matchId, route);
|
|
399
|
+
const head = headResult ? await headResult : void 0;
|
|
400
|
+
const pendingPromise = match._nonReactive.minPendingPromise;
|
|
401
|
+
if (pendingPromise) await pendingPromise;
|
|
402
|
+
if (route._componentsPromise) await route._componentsPromise;
|
|
403
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
404
|
+
...prev,
|
|
405
|
+
error: void 0,
|
|
406
|
+
status: "success",
|
|
407
|
+
isFetching: false,
|
|
408
|
+
updatedAt: Date.now(),
|
|
409
|
+
...head
|
|
410
|
+
}));
|
|
411
|
+
} catch (e) {
|
|
412
|
+
let error = e;
|
|
413
|
+
const pendingPromise = match._nonReactive.minPendingPromise;
|
|
414
|
+
if (pendingPromise) await pendingPromise;
|
|
415
|
+
handleRedirectAndNotFound(inner, inner.router.getMatch(matchId), e);
|
|
416
|
+
try {
|
|
417
|
+
route.options.onError?.(e);
|
|
418
|
+
} catch (onErrorError) {
|
|
419
|
+
error = onErrorError;
|
|
420
|
+
handleRedirectAndNotFound(
|
|
421
|
+
inner,
|
|
422
|
+
inner.router.getMatch(matchId),
|
|
423
|
+
onErrorError
|
|
424
|
+
);
|
|
425
|
+
}
|
|
426
|
+
const headResult = executeHead(inner, matchId, route);
|
|
427
|
+
const head = headResult ? await headResult : void 0;
|
|
428
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
429
|
+
...prev,
|
|
430
|
+
error,
|
|
431
|
+
status: "error",
|
|
432
|
+
isFetching: false,
|
|
433
|
+
...head
|
|
434
|
+
}));
|
|
435
|
+
}
|
|
436
|
+
} catch (err) {
|
|
437
|
+
const match = inner.router.getMatch(matchId);
|
|
438
|
+
if (match) {
|
|
439
|
+
const headResult = executeHead(inner, matchId, route);
|
|
440
|
+
if (headResult) {
|
|
441
|
+
const head = await headResult;
|
|
442
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
443
|
+
...prev,
|
|
444
|
+
...head
|
|
445
|
+
}));
|
|
446
|
+
}
|
|
447
|
+
match._nonReactive.loaderPromise = void 0;
|
|
448
|
+
}
|
|
449
|
+
handleRedirectAndNotFound(inner, match, err);
|
|
450
|
+
}
|
|
451
|
+
};
|
|
452
|
+
const loadRouteMatch = async (inner, index) => {
|
|
453
|
+
const { id: matchId, routeId } = inner.matches[index];
|
|
454
|
+
let loaderShouldRunAsync = false;
|
|
455
|
+
let loaderIsRunningAsync = false;
|
|
456
|
+
const route = inner.router.looseRoutesById[routeId];
|
|
457
|
+
if (shouldSkipLoader(inner, matchId)) {
|
|
458
|
+
if (inner.router.isServer) {
|
|
459
|
+
const headResult = executeHead(inner, matchId, route);
|
|
460
|
+
if (headResult) {
|
|
461
|
+
const head = await headResult;
|
|
462
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
463
|
+
...prev,
|
|
464
|
+
...head
|
|
465
|
+
}));
|
|
466
|
+
}
|
|
467
|
+
return inner.router.getMatch(matchId);
|
|
468
|
+
}
|
|
469
|
+
} else {
|
|
470
|
+
const prevMatch = inner.router.getMatch(matchId);
|
|
471
|
+
if (prevMatch._nonReactive.loaderPromise) {
|
|
472
|
+
if (prevMatch.status === "success" && !inner.sync && !prevMatch.preload) {
|
|
473
|
+
return prevMatch;
|
|
474
|
+
}
|
|
475
|
+
await prevMatch._nonReactive.loaderPromise;
|
|
476
|
+
const match2 = inner.router.getMatch(matchId);
|
|
477
|
+
if (match2.error) {
|
|
478
|
+
handleRedirectAndNotFound(inner, match2, match2.error);
|
|
479
|
+
}
|
|
480
|
+
} else {
|
|
481
|
+
const age = Date.now() - prevMatch.updatedAt;
|
|
482
|
+
const preload = resolvePreload(inner, matchId);
|
|
483
|
+
const staleAge = preload ? route.options.preloadStaleTime ?? inner.router.options.defaultPreloadStaleTime ?? 3e4 : route.options.staleTime ?? inner.router.options.defaultStaleTime ?? 0;
|
|
484
|
+
const shouldReloadOption = route.options.shouldReload;
|
|
485
|
+
const shouldReload = typeof shouldReloadOption === "function" ? shouldReloadOption(getLoaderContext(inner, matchId, index, route)) : shouldReloadOption;
|
|
486
|
+
const nextPreload = !!preload && !inner.router.state.matches.some((d) => d.id === matchId);
|
|
487
|
+
const match2 = inner.router.getMatch(matchId);
|
|
488
|
+
match2._nonReactive.loaderPromise = utils.createControlledPromise();
|
|
489
|
+
if (nextPreload !== match2.preload) {
|
|
490
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
491
|
+
...prev,
|
|
492
|
+
preload: nextPreload
|
|
493
|
+
}));
|
|
494
|
+
}
|
|
495
|
+
const { status, invalid } = match2;
|
|
496
|
+
loaderShouldRunAsync = status === "success" && (invalid || (shouldReload ?? age > staleAge));
|
|
497
|
+
if (preload && route.options.preload === false) ;
|
|
498
|
+
else if (loaderShouldRunAsync && !inner.sync) {
|
|
499
|
+
loaderIsRunningAsync = true;
|
|
500
|
+
(async () => {
|
|
501
|
+
try {
|
|
502
|
+
await runLoader(inner, matchId, index, route);
|
|
503
|
+
const match3 = inner.router.getMatch(matchId);
|
|
504
|
+
match3._nonReactive.loaderPromise?.resolve();
|
|
505
|
+
match3._nonReactive.loadPromise?.resolve();
|
|
506
|
+
match3._nonReactive.loaderPromise = void 0;
|
|
507
|
+
} catch (err) {
|
|
508
|
+
if (redirect.isRedirect(err)) {
|
|
509
|
+
await inner.router.navigate(err.options);
|
|
510
|
+
}
|
|
511
|
+
}
|
|
512
|
+
})();
|
|
513
|
+
} else if (status !== "success" || loaderShouldRunAsync && inner.sync) {
|
|
514
|
+
await runLoader(inner, matchId, index, route);
|
|
515
|
+
} else {
|
|
516
|
+
const headResult = executeHead(inner, matchId, route);
|
|
517
|
+
if (headResult) {
|
|
518
|
+
const head = await headResult;
|
|
519
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
520
|
+
...prev,
|
|
521
|
+
...head
|
|
522
|
+
}));
|
|
523
|
+
}
|
|
524
|
+
}
|
|
525
|
+
}
|
|
526
|
+
}
|
|
527
|
+
const match = inner.router.getMatch(matchId);
|
|
528
|
+
if (!loaderIsRunningAsync) {
|
|
529
|
+
match._nonReactive.loaderPromise?.resolve();
|
|
530
|
+
match._nonReactive.loadPromise?.resolve();
|
|
531
|
+
}
|
|
532
|
+
clearTimeout(match._nonReactive.pendingTimeout);
|
|
533
|
+
match._nonReactive.pendingTimeout = void 0;
|
|
534
|
+
if (!loaderIsRunningAsync) match._nonReactive.loaderPromise = void 0;
|
|
535
|
+
match._nonReactive.dehydrated = void 0;
|
|
536
|
+
const nextIsFetching = loaderIsRunningAsync ? match.isFetching : false;
|
|
537
|
+
if (nextIsFetching !== match.isFetching || match.invalid !== false) {
|
|
538
|
+
inner.updateMatch(matchId, (prev) => ({
|
|
539
|
+
...prev,
|
|
540
|
+
isFetching: nextIsFetching,
|
|
541
|
+
invalid: false
|
|
542
|
+
}));
|
|
543
|
+
return inner.router.getMatch(matchId);
|
|
544
|
+
} else {
|
|
545
|
+
return match;
|
|
546
|
+
}
|
|
547
|
+
};
|
|
548
|
+
async function loadMatches(arg) {
|
|
549
|
+
const inner = Object.assign(arg, {
|
|
550
|
+
matchPromises: []
|
|
551
|
+
});
|
|
552
|
+
if (!inner.router.isServer && inner.router.state.matches.some((d) => d._forcePending)) {
|
|
553
|
+
triggerOnReady(inner);
|
|
554
|
+
}
|
|
555
|
+
try {
|
|
556
|
+
for (let i = 0; i < inner.matches.length; i++) {
|
|
557
|
+
const beforeLoad = handleBeforeLoad(inner, i);
|
|
558
|
+
if (utils.isPromise(beforeLoad)) await beforeLoad;
|
|
559
|
+
}
|
|
560
|
+
const max = inner.firstBadMatchIndex ?? inner.matches.length;
|
|
561
|
+
for (let i = 0; i < max; i++) {
|
|
562
|
+
inner.matchPromises.push(loadRouteMatch(inner, i));
|
|
563
|
+
}
|
|
564
|
+
await Promise.all(inner.matchPromises);
|
|
565
|
+
const readyPromise = triggerOnReady(inner);
|
|
566
|
+
if (utils.isPromise(readyPromise)) await readyPromise;
|
|
567
|
+
} catch (err) {
|
|
568
|
+
if (notFound.isNotFound(err) && !inner.preload) {
|
|
569
|
+
const readyPromise = triggerOnReady(inner);
|
|
570
|
+
if (utils.isPromise(readyPromise)) await readyPromise;
|
|
571
|
+
throw err;
|
|
572
|
+
}
|
|
573
|
+
if (redirect.isRedirect(err)) {
|
|
574
|
+
throw err;
|
|
575
|
+
}
|
|
576
|
+
}
|
|
577
|
+
return inner.matches;
|
|
578
|
+
}
|
|
579
|
+
async function loadRouteChunk(route) {
|
|
580
|
+
if (!route._lazyLoaded && route._lazyPromise === void 0) {
|
|
581
|
+
if (route.lazyFn) {
|
|
582
|
+
route._lazyPromise = route.lazyFn().then((lazyRoute) => {
|
|
583
|
+
const { id: _id, ...options } = lazyRoute.options;
|
|
584
|
+
Object.assign(route.options, options);
|
|
585
|
+
route._lazyLoaded = true;
|
|
586
|
+
route._lazyPromise = void 0;
|
|
587
|
+
});
|
|
588
|
+
} else {
|
|
589
|
+
route._lazyLoaded = true;
|
|
590
|
+
}
|
|
591
|
+
}
|
|
592
|
+
if (!route._componentsLoaded && route._componentsPromise === void 0) {
|
|
593
|
+
const loadComponents = () => {
|
|
594
|
+
const preloads = [];
|
|
595
|
+
for (const type of componentTypes) {
|
|
596
|
+
const preload = route.options[type]?.preload;
|
|
597
|
+
if (preload) preloads.push(preload());
|
|
598
|
+
}
|
|
599
|
+
if (preloads.length)
|
|
600
|
+
return Promise.all(preloads).then(() => {
|
|
601
|
+
route._componentsLoaded = true;
|
|
602
|
+
route._componentsPromise = void 0;
|
|
603
|
+
});
|
|
604
|
+
route._componentsLoaded = true;
|
|
605
|
+
route._componentsPromise = void 0;
|
|
606
|
+
return;
|
|
607
|
+
};
|
|
608
|
+
route._componentsPromise = route._lazyPromise ? route._lazyPromise.then(loadComponents) : loadComponents();
|
|
609
|
+
}
|
|
610
|
+
return route._componentsPromise;
|
|
611
|
+
}
|
|
612
|
+
function makeMaybe(value, error) {
|
|
613
|
+
if (error) {
|
|
614
|
+
return { status: "error", error };
|
|
615
|
+
}
|
|
616
|
+
return { status: "success", value };
|
|
617
|
+
}
|
|
618
|
+
function routeNeedsPreload(route) {
|
|
619
|
+
for (const componentType of componentTypes) {
|
|
620
|
+
if (route.options[componentType]?.preload) {
|
|
621
|
+
return true;
|
|
622
|
+
}
|
|
623
|
+
}
|
|
624
|
+
return false;
|
|
625
|
+
}
|
|
626
|
+
const componentTypes = [
|
|
627
|
+
"component",
|
|
628
|
+
"errorComponent",
|
|
629
|
+
"pendingComponent",
|
|
630
|
+
"notFoundComponent"
|
|
631
|
+
];
|
|
632
|
+
exports.componentTypes = componentTypes;
|
|
633
|
+
exports.loadMatches = loadMatches;
|
|
634
|
+
exports.loadRouteChunk = loadRouteChunk;
|
|
635
|
+
exports.routeNeedsPreload = routeNeedsPreload;
|
|
636
|
+
//# sourceMappingURL=load-matches.cjs.map
|