@reckona/mreact-router 0.0.141 → 0.0.142
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/README.md +4 -2
- package/dist/actions.d.ts +1 -1
- package/dist/actions.d.ts.map +1 -1
- package/dist/actions.js +28 -8
- package/dist/actions.js.map +1 -1
- package/dist/adapters/cloudflare.d.ts.map +1 -1
- package/dist/adapters/cloudflare.js +31 -12
- package/dist/adapters/cloudflare.js.map +1 -1
- package/dist/build.d.ts.map +1 -1
- package/dist/build.js +470 -12
- package/dist/build.js.map +1 -1
- package/dist/cli-options.js +1 -1
- package/dist/cli-options.js.map +1 -1
- package/dist/client-route-inference.d.ts +1 -1
- package/dist/client-route-inference.d.ts.map +1 -1
- package/dist/client-route-inference.js +1 -1
- package/dist/client-route-inference.js.map +1 -1
- package/dist/client.d.ts +8 -1
- package/dist/client.d.ts.map +1 -1
- package/dist/client.js +16 -0
- package/dist/client.js.map +1 -1
- package/dist/config.js +1 -1
- package/dist/config.js.map +1 -1
- package/dist/import-policy.js +7 -0
- package/dist/import-policy.js.map +1 -1
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/metadata.d.ts +1 -0
- package/dist/metadata.d.ts.map +1 -1
- package/dist/metadata.js +288 -1
- package/dist/metadata.js.map +1 -1
- package/dist/middleware.d.ts +5 -0
- package/dist/middleware.d.ts.map +1 -1
- package/dist/middleware.js +13 -0
- package/dist/middleware.js.map +1 -1
- package/dist/render.d.ts.map +1 -1
- package/dist/render.js +41 -9
- package/dist/render.js.map +1 -1
- package/dist/typed-routes.d.ts +24 -0
- package/dist/typed-routes.d.ts.map +1 -0
- package/dist/typed-routes.js +60 -0
- package/dist/typed-routes.js.map +1 -0
- package/dist/vite.d.ts.map +1 -1
- package/dist/vite.js +22 -1
- package/dist/vite.js.map +1 -1
- package/package.json +11 -11
- package/src/actions.ts +39 -12
- package/src/adapters/cloudflare.ts +48 -12
- package/src/build.ts +491 -11
- package/src/cli-options.ts +1 -1
- package/src/client-route-inference.ts +1 -0
- package/src/client.ts +28 -1
- package/src/config.ts +1 -1
- package/src/import-policy.ts +8 -0
- package/src/index.ts +9 -0
- package/src/metadata.ts +388 -1
- package/src/middleware.ts +22 -0
- package/src/render.ts +58 -7
- package/src/typed-routes.ts +121 -0
- package/src/vite.ts +25 -0
|
@@ -5,6 +5,7 @@ import {
|
|
|
5
5
|
__MREACT_QUERY_STATE_SCRIPT_ID,
|
|
6
6
|
createQueryClient,
|
|
7
7
|
dehydrate,
|
|
8
|
+
isQueryClientScopeUnavailableError,
|
|
8
9
|
runWithQueryClient,
|
|
9
10
|
type DehydratedQueryClient,
|
|
10
11
|
type QueryClient,
|
|
@@ -26,7 +27,9 @@ import {
|
|
|
26
27
|
} from "../logger.js";
|
|
27
28
|
import { normalizeRoutePath } from "../route-path.js";
|
|
28
29
|
import type { AppRoute } from "../routes.js";
|
|
30
|
+
import { contentSecurityPolicy } from "../csp.js";
|
|
29
31
|
import { isNotFoundError } from "../navigation.js";
|
|
32
|
+
import { validateRouteMetadata } from "../metadata.js";
|
|
30
33
|
import { routeSecurityHeaders } from "../security-headers.js";
|
|
31
34
|
import type { AppRouterPrerenderStore } from "../serve.js";
|
|
32
35
|
import { emitRouterDevtoolsEvent } from "./devtools.js";
|
|
@@ -361,7 +364,7 @@ export function createCloudflareRouteModuleRenderer<Env = unknown>(
|
|
|
361
364
|
data =
|
|
362
365
|
pageModule.loader === undefined
|
|
363
366
|
? undefined
|
|
364
|
-
: await
|
|
367
|
+
: await runWithCloudflareQueryClient(queryClient, () => pageModule.loader!(loaderContext));
|
|
365
368
|
} catch (error) {
|
|
366
369
|
if (error instanceof Response) {
|
|
367
370
|
return error;
|
|
@@ -382,7 +385,7 @@ export function createCloudflareRouteModuleRenderer<Env = unknown>(
|
|
|
382
385
|
let rendered: Awaited<ReturnType<typeof component>>;
|
|
383
386
|
|
|
384
387
|
try {
|
|
385
|
-
rendered = await
|
|
388
|
+
rendered = await runWithCloudflareQueryClient(queryClient, () => component(props));
|
|
386
389
|
} catch (error) {
|
|
387
390
|
if (isNotFoundError(error)) {
|
|
388
391
|
return cloudflareNotFoundResponse(request);
|
|
@@ -391,14 +394,15 @@ export function createCloudflareRouteModuleRenderer<Env = unknown>(
|
|
|
391
394
|
throw error;
|
|
392
395
|
}
|
|
393
396
|
|
|
397
|
+
const metadata = await runWithCloudflareQueryClient(queryClient, () =>
|
|
398
|
+
resolveCloudflareRouteMetadata([pageModule], props),
|
|
399
|
+
);
|
|
400
|
+
|
|
394
401
|
if (rendered instanceof Response) {
|
|
395
|
-
return withDefaultSecurityHeaders(rendered, request);
|
|
402
|
+
return withDefaultSecurityHeaders(rendered, request, metadata);
|
|
396
403
|
}
|
|
397
404
|
|
|
398
405
|
const modulePreload = cloudflareModulePreloadTag(context.clientManifest, context.route.path);
|
|
399
|
-
const metadata = await runWithQueryClient(queryClient, () =>
|
|
400
|
-
resolveCloudflareRouteMetadata([pageModule], props),
|
|
401
|
-
);
|
|
402
406
|
const body = withCloudflareHydrationMarkers({
|
|
403
407
|
data,
|
|
404
408
|
html: rendered,
|
|
@@ -410,7 +414,7 @@ export function createCloudflareRouteModuleRenderer<Env = unknown>(
|
|
|
410
414
|
const documented =
|
|
411
415
|
options.document === undefined
|
|
412
416
|
? defaultCloudflareDocument(body, modulePreload, metadata)
|
|
413
|
-
: await
|
|
417
|
+
: await runWithCloudflareQueryClient(queryClient, () =>
|
|
414
418
|
options.document!({
|
|
415
419
|
...props,
|
|
416
420
|
body,
|
|
@@ -429,6 +433,7 @@ export function createCloudflareRouteModuleRenderer<Env = unknown>(
|
|
|
429
433
|
headers: { "content-type": "text/html; charset=utf-8" },
|
|
430
434
|
}),
|
|
431
435
|
request,
|
|
436
|
+
metadata,
|
|
432
437
|
);
|
|
433
438
|
};
|
|
434
439
|
}
|
|
@@ -469,6 +474,18 @@ function injectCloudflareQueryStateScript(html: string, state: DehydratedQueryCl
|
|
|
469
474
|
: `${html}${script}`;
|
|
470
475
|
}
|
|
471
476
|
|
|
477
|
+
function runWithCloudflareQueryClient<T>(queryClient: QueryClient, fn: () => T): T {
|
|
478
|
+
try {
|
|
479
|
+
return runWithQueryClient(queryClient, fn);
|
|
480
|
+
} catch (error) {
|
|
481
|
+
if (isQueryClientScopeUnavailableError(error)) {
|
|
482
|
+
return fn();
|
|
483
|
+
}
|
|
484
|
+
|
|
485
|
+
throw error;
|
|
486
|
+
}
|
|
487
|
+
}
|
|
488
|
+
|
|
472
489
|
async function dispatchCloudflareServerRoute<Env>(
|
|
473
490
|
module: CloudflareServerRouteModule<Env>,
|
|
474
491
|
request: Request,
|
|
@@ -675,10 +692,25 @@ function cloudflareDocumentReloadNavigationResponse(): Response {
|
|
|
675
692
|
});
|
|
676
693
|
}
|
|
677
694
|
|
|
678
|
-
function withDefaultSecurityHeaders(
|
|
695
|
+
function withDefaultSecurityHeaders(
|
|
696
|
+
response: Response,
|
|
697
|
+
request: Request,
|
|
698
|
+
metadata?: RouteMetadata | undefined,
|
|
699
|
+
): Response {
|
|
679
700
|
const headers = new Headers(response.headers);
|
|
701
|
+
const csp = contentSecurityPolicy(metadata?.csp);
|
|
680
702
|
|
|
681
|
-
|
|
703
|
+
if (
|
|
704
|
+
isHtmlContentType(headers.get("content-type")) &&
|
|
705
|
+
csp !== undefined &&
|
|
706
|
+
!headers.has("content-security-policy")
|
|
707
|
+
) {
|
|
708
|
+
headers.set("content-security-policy", csp);
|
|
709
|
+
}
|
|
710
|
+
|
|
711
|
+
for (const [name, value] of Object.entries(
|
|
712
|
+
routeSecurityHeaders({ request, security: metadata?.security }),
|
|
713
|
+
)) {
|
|
682
714
|
if (!headers.has(name)) {
|
|
683
715
|
headers.set(name, value);
|
|
684
716
|
}
|
|
@@ -1343,11 +1375,15 @@ async function resolveCloudflareRouteMetadata<Data, Env>(
|
|
|
1343
1375
|
const metadata: RouteMetadata[] = [];
|
|
1344
1376
|
|
|
1345
1377
|
for (const module of modules) {
|
|
1346
|
-
let next = module.metadata;
|
|
1378
|
+
let next = validateRouteMetadata(module.metadata);
|
|
1347
1379
|
|
|
1348
1380
|
if (module.generateMetadata !== undefined) {
|
|
1349
1381
|
const generated = await module.generateMetadata(context);
|
|
1350
|
-
next = mergeCloudflareRouteMetadata(
|
|
1382
|
+
next = mergeCloudflareRouteMetadata(
|
|
1383
|
+
[next, validateRouteMetadata(generated, "generateMetadata")].filter(
|
|
1384
|
+
isCloudflareRouteMetadata,
|
|
1385
|
+
),
|
|
1386
|
+
);
|
|
1351
1387
|
}
|
|
1352
1388
|
|
|
1353
1389
|
if (next !== undefined) {
|
|
@@ -1355,7 +1391,7 @@ async function resolveCloudflareRouteMetadata<Data, Env>(
|
|
|
1355
1391
|
}
|
|
1356
1392
|
}
|
|
1357
1393
|
|
|
1358
|
-
return mergeCloudflareRouteMetadata(metadata);
|
|
1394
|
+
return validateRouteMetadata(mergeCloudflareRouteMetadata(metadata));
|
|
1359
1395
|
}
|
|
1360
1396
|
|
|
1361
1397
|
function isCloudflareRouteMetadata(value: RouteMetadata | undefined): value is RouteMetadata {
|