@reckona/mreact-router 0.0.86 → 0.0.87
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/bundle-pipeline.d.ts +1 -0
- package/dist/bundle-pipeline.d.ts.map +1 -1
- package/dist/bundle-pipeline.js +115 -6
- package/dist/bundle-pipeline.js.map +1 -1
- package/dist/client.d.ts.map +1 -1
- package/dist/client.js +13 -15
- package/dist/client.js.map +1 -1
- package/dist/module-runner.d.ts +2 -0
- package/dist/module-runner.d.ts.map +1 -1
- package/dist/module-runner.js +31 -2
- package/dist/module-runner.js.map +1 -1
- package/dist/render.d.ts +1 -0
- package/dist/render.d.ts.map +1 -1
- package/dist/render.js +24 -5
- package/dist/render.js.map +1 -1
- package/dist/vite.d.ts.map +1 -1
- package/dist/vite.js +18 -20
- package/dist/vite.js.map +1 -1
- package/package.json +11 -11
- package/src/bundle-pipeline.ts +157 -24
- package/src/client.ts +23 -32
- package/src/module-runner.ts +37 -2
- package/src/render.ts +59 -30
- package/src/vite.ts +33 -37
package/src/client.ts
CHANGED
|
@@ -938,14 +938,7 @@ function isStyleModuleSpecifier(source: string): boolean {
|
|
|
938
938
|
return styleModuleExtensions.has(extname(pathname));
|
|
939
939
|
}
|
|
940
940
|
|
|
941
|
-
const styleModuleExtensions = new Set([
|
|
942
|
-
".css",
|
|
943
|
-
".less",
|
|
944
|
-
".sass",
|
|
945
|
-
".scss",
|
|
946
|
-
".styl",
|
|
947
|
-
".stylus",
|
|
948
|
-
]);
|
|
941
|
+
const styleModuleExtensions = new Set([".css", ".less", ".sass", ".scss", ".styl", ".stylus"]);
|
|
949
942
|
|
|
950
943
|
function renderedImportedExportNames(
|
|
951
944
|
reference: ClientRouteStaticImportReference,
|
|
@@ -1272,13 +1265,10 @@ function hasViteTransformHook(plugin: Plugin): boolean {
|
|
|
1272
1265
|
return viteTransformHookHandler(plugin) !== undefined;
|
|
1273
1266
|
}
|
|
1274
1267
|
|
|
1275
|
-
function viteTransformHookHandler(
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
id: string,
|
|
1280
|
-
options?: { ssr?: boolean | undefined },
|
|
1281
|
-
) => unknown)
|
|
1268
|
+
function viteTransformHookHandler(
|
|
1269
|
+
plugin: Plugin,
|
|
1270
|
+
):
|
|
1271
|
+
| ((this: unknown, code: string, id: string, options?: { ssr?: boolean | undefined }) => unknown)
|
|
1282
1272
|
| undefined {
|
|
1283
1273
|
const transform = plugin.transform as unknown;
|
|
1284
1274
|
|
|
@@ -1580,8 +1570,7 @@ export async function buildClientRouteEntrySource(
|
|
|
1580
1570
|
routeSourceAnalysis,
|
|
1581
1571
|
options.filename,
|
|
1582
1572
|
);
|
|
1583
|
-
const routeHasEventBindings =
|
|
1584
|
-
(compiled.metadata.eventHydrationManifest?.events.length ?? 0) > 0;
|
|
1573
|
+
const routeHasEventBindings = (compiled.metadata.eventHydrationManifest?.events.length ?? 0) > 0;
|
|
1585
1574
|
const routeRequiresFullHydration =
|
|
1586
1575
|
routeExplicitlyRequiresHydration ||
|
|
1587
1576
|
routeUsesCells ||
|
|
@@ -1695,8 +1684,9 @@ __mreactGlobal.__mreactRouteCell = (nativeCell, initial) => {
|
|
|
1695
1684
|
`
|
|
1696
1685
|
: "";
|
|
1697
1686
|
const routeCellHydrationIndent = routeUsesCells ? " " : " ";
|
|
1698
|
-
const routeCleanupHydrationStart =
|
|
1699
|
-
|
|
1687
|
+
const routeCleanupHydrationStart =
|
|
1688
|
+
routeUsesCleanupScope && !routeUsesCells
|
|
1689
|
+
? ` __mreactDisposeRoute(__mreactRouteId);
|
|
1700
1690
|
const __mreactRouteEffectDisposers = new Set();
|
|
1701
1691
|
__mreactRouteDisposers.set(__mreactRouteId, () => {
|
|
1702
1692
|
for (const __mreactDispose of Array.from(__mreactRouteEffectDisposers)) {
|
|
@@ -1705,7 +1695,7 @@ __mreactGlobal.__mreactRouteCell = (nativeCell, initial) => {
|
|
|
1705
1695
|
__mreactRouteEffectDisposers.clear();
|
|
1706
1696
|
});
|
|
1707
1697
|
`
|
|
1708
|
-
|
|
1698
|
+
: "";
|
|
1709
1699
|
const routeCellDropFunction = routeUsesCells
|
|
1710
1700
|
? `
|
|
1711
1701
|
function __mreactDropMismatchedRouteState(previousState, nextState) {
|
|
@@ -3235,6 +3225,15 @@ function workspaceRuntimePlugin(options: { routeFiles: readonly string[] }) {
|
|
|
3235
3225
|
"@reckona/mreact-compat",
|
|
3236
3226
|
];
|
|
3237
3227
|
const runtimePaths = new Map([
|
|
3228
|
+
["react", reactCompatPath],
|
|
3229
|
+
["react-dom", reactCompatPath],
|
|
3230
|
+
["react-dom/client", reactCompatPath],
|
|
3231
|
+
["react-dom/server", reactCompatPath],
|
|
3232
|
+
[
|
|
3233
|
+
"react/jsx-dev-runtime",
|
|
3234
|
+
packageFile("react-compat", "@reckona/mreact-compat", "jsx-dev-runtime"),
|
|
3235
|
+
],
|
|
3236
|
+
["react/jsx-runtime", packageFile("react-compat", "@reckona/mreact-compat", "jsx-runtime")],
|
|
3238
3237
|
[
|
|
3239
3238
|
"@reckona/mreact-reactive-core/internal",
|
|
3240
3239
|
packageFile("reactive-core", "@reckona/mreact-reactive-core", "internal"),
|
|
@@ -3264,10 +3263,7 @@ function workspaceRuntimePlugin(options: { routeFiles: readonly string[] }) {
|
|
|
3264
3263
|
"@reckona/mreact-compat/scheduler",
|
|
3265
3264
|
packageFile("react-compat", "@reckona/mreact-compat", "scheduler"),
|
|
3266
3265
|
],
|
|
3267
|
-
[
|
|
3268
|
-
"@reckona/mreact-reactive-dom",
|
|
3269
|
-
reactiveDomPath,
|
|
3270
|
-
],
|
|
3266
|
+
["@reckona/mreact-reactive-dom", reactiveDomPath],
|
|
3271
3267
|
]);
|
|
3272
3268
|
|
|
3273
3269
|
return {
|
|
@@ -3295,7 +3291,7 @@ function workspaceRuntimePlugin(options: { routeFiles: readonly string[] }) {
|
|
|
3295
3291
|
buildApi.onResolve(
|
|
3296
3292
|
{
|
|
3297
3293
|
filter:
|
|
3298
|
-
|
|
3294
|
+
/^(?:react(?:\/jsx-(?:dev-)?runtime)?|react-dom(?:\/(?:client|server))?|@reckona\/mreact-(?:compat|reactive-core|reactive-dom)(?:\/(?:event-priority|flight|internal|jsx-dev-runtime|jsx-runtime|scheduler))?)$/,
|
|
3299
3295
|
},
|
|
3300
3296
|
(args) => {
|
|
3301
3297
|
const path = runtimePaths.get(args.path);
|
|
@@ -3381,9 +3377,7 @@ function importerInRuntimePackage(
|
|
|
3381
3377
|
const normalizedImporter = importer.split(/[\\/]+/).join("/");
|
|
3382
3378
|
return (
|
|
3383
3379
|
directories.some((directory) => importer.startsWith(`${directory}${sep}`)) ||
|
|
3384
|
-
packageNames.some((packageName) =>
|
|
3385
|
-
normalizedImporter.includes(`/node_modules/${packageName}/`),
|
|
3386
|
-
)
|
|
3380
|
+
packageNames.some((packageName) => normalizedImporter.includes(`/node_modules/${packageName}/`))
|
|
3387
3381
|
);
|
|
3388
3382
|
}
|
|
3389
3383
|
|
|
@@ -3421,10 +3415,7 @@ function detectRouteCellStateHint(code: string): boolean {
|
|
|
3421
3415
|
}
|
|
3422
3416
|
|
|
3423
3417
|
function detectRouteReactiveEffectHint(code: string): boolean {
|
|
3424
|
-
return (
|
|
3425
|
-
/from\s+["']@reckona\/mreact-reactive-core["']/.test(code) &&
|
|
3426
|
-
/\beffect\s*\(/.test(code)
|
|
3427
|
-
);
|
|
3418
|
+
return /from\s+["']@reckona\/mreact-reactive-core["']/.test(code) && /\beffect\s*\(/.test(code);
|
|
3428
3419
|
}
|
|
3429
3420
|
|
|
3430
3421
|
async function inferClientReferenceManifestForBundle(options: {
|
package/src/module-runner.ts
CHANGED
|
@@ -69,6 +69,7 @@ export function routerModuleRunnerRuntimeCacheStats(): RouterRuntimeCacheStat[]
|
|
|
69
69
|
export async function importAppRouterSourceModule<T>(options: {
|
|
70
70
|
cacheKey?: string | undefined;
|
|
71
71
|
code: string;
|
|
72
|
+
externalizeAppSourceModuleDirs?: readonly string[] | undefined;
|
|
72
73
|
label: string;
|
|
73
74
|
resolveDir?: string | undefined;
|
|
74
75
|
serverSourceTransform?: ServerSourceTransformOptions | undefined;
|
|
@@ -107,6 +108,7 @@ export async function importAppRouterSourceModule<T>(options: {
|
|
|
107
108
|
|
|
108
109
|
async function importAppRouterSourceModuleWithoutCache<T>(options: {
|
|
109
110
|
code: string;
|
|
111
|
+
externalizeAppSourceModuleDirs?: readonly string[] | undefined;
|
|
110
112
|
label: string;
|
|
111
113
|
resolveDir?: string | undefined;
|
|
112
114
|
serverSourceTransform?: ServerSourceTransformOptions | undefined;
|
|
@@ -116,7 +118,10 @@ async function importAppRouterSourceModuleWithoutCache<T>(options: {
|
|
|
116
118
|
const code =
|
|
117
119
|
options.resolveDir === undefined ? options.code : await bundleAppRouterSourceModule(options);
|
|
118
120
|
const executableCode = withNodeRequireShimForEsmBundle({
|
|
119
|
-
code
|
|
121
|
+
code: withFileImportMetaUrl(
|
|
122
|
+
code,
|
|
123
|
+
options.sourcefile ?? join(options.resolveDir ?? process.cwd(), "module.js"),
|
|
124
|
+
),
|
|
120
125
|
requireBaseDir:
|
|
121
126
|
options.resolveDir ??
|
|
122
127
|
(options.sourcefile === undefined ? undefined : dirname(options.sourcefile)),
|
|
@@ -174,6 +179,7 @@ export async function importAppRouterBuiltFileModule<T>(options: {
|
|
|
174
179
|
|
|
175
180
|
export async function bundleAppRouterSourceModule(options: {
|
|
176
181
|
code: string;
|
|
182
|
+
externalizeAppSourceModuleDirs?: readonly string[] | undefined;
|
|
177
183
|
label: string;
|
|
178
184
|
resolveDir?: string | undefined;
|
|
179
185
|
serverSourceTransform?: ServerSourceTransformOptions | undefined;
|
|
@@ -182,6 +188,7 @@ export async function bundleAppRouterSourceModule(options: {
|
|
|
182
188
|
}): Promise<string> {
|
|
183
189
|
const output = await bundleRouterModule({
|
|
184
190
|
code: options.code,
|
|
191
|
+
externalizeAppSourceModuleDirs: options.externalizeAppSourceModuleDirs,
|
|
185
192
|
filename: options.sourcefile ?? join(options.resolveDir ?? process.cwd(), "module.js"),
|
|
186
193
|
platform: "node",
|
|
187
194
|
vitePlugins: options.vitePlugins,
|
|
@@ -419,6 +426,34 @@ function workspacePackageResolutionPlugin() {
|
|
|
419
426
|
specifier,
|
|
420
427
|
});
|
|
421
428
|
const entries = new Map<string, { entry: string; monorepoDir: string; packageName: string }>([
|
|
429
|
+
[
|
|
430
|
+
"react",
|
|
431
|
+
{ entry: "index", monorepoDir: "react-compat", packageName: "@reckona/mreact-compat" },
|
|
432
|
+
],
|
|
433
|
+
[
|
|
434
|
+
"react-dom",
|
|
435
|
+
{ entry: "index", monorepoDir: "react-compat", packageName: "@reckona/mreact-compat" },
|
|
436
|
+
],
|
|
437
|
+
[
|
|
438
|
+
"react-dom/client",
|
|
439
|
+
{ entry: "index", monorepoDir: "react-compat", packageName: "@reckona/mreact-compat" },
|
|
440
|
+
],
|
|
441
|
+
[
|
|
442
|
+
"react-dom/server",
|
|
443
|
+
{ entry: "index", monorepoDir: "react-compat", packageName: "@reckona/mreact-compat" },
|
|
444
|
+
],
|
|
445
|
+
[
|
|
446
|
+
"react/jsx-dev-runtime",
|
|
447
|
+
{
|
|
448
|
+
entry: "jsx-dev-runtime",
|
|
449
|
+
monorepoDir: "react-compat",
|
|
450
|
+
packageName: "@reckona/mreact-compat",
|
|
451
|
+
},
|
|
452
|
+
],
|
|
453
|
+
[
|
|
454
|
+
"react/jsx-runtime",
|
|
455
|
+
{ entry: "jsx-runtime", monorepoDir: "react-compat", packageName: "@reckona/mreact-compat" },
|
|
456
|
+
],
|
|
422
457
|
["@reckona/mreact", { entry: "index", monorepoDir: "react", packageName: "@reckona/mreact" }],
|
|
423
458
|
[
|
|
424
459
|
"@reckona/mreact/jsx-dev-runtime",
|
|
@@ -503,7 +538,7 @@ function workspacePackageResolutionPlugin() {
|
|
|
503
538
|
buildApi.onResolve(
|
|
504
539
|
{
|
|
505
540
|
filter:
|
|
506
|
-
|
|
541
|
+
/^(?:react(?:\/jsx-(?:dev-)?runtime)?|react-dom(?:\/(?:client|server))?|@reckona\/(?:mreact(?:\/(?:jsx-dev-runtime|jsx-runtime))?|mreact-(?:auth|query|reactive-core|server|router|compat)(?:\/(?:event-priority|flight|internal|jsx-dev-runtime|jsx-runtime|scheduler|app-router-globals|link|native-escape|navigation-state|session|stream-list|internal\/native-escape|internal\/session))?))$/,
|
|
507
542
|
},
|
|
508
543
|
(args) => {
|
|
509
544
|
const routerPath = routerEntries.get(args.path);
|
package/src/render.ts
CHANGED
|
@@ -1,11 +1,8 @@
|
|
|
1
1
|
import { randomUUID } from "node:crypto";
|
|
2
2
|
import { AsyncLocalStorage } from "node:async_hooks";
|
|
3
3
|
import { access, readFile, stat } from "node:fs/promises";
|
|
4
|
-
import { dirname, join, relative, sep } from "node:path";
|
|
5
|
-
import {
|
|
6
|
-
formatDiagnostic,
|
|
7
|
-
transform,
|
|
8
|
-
} from "@reckona/mreact-compiler";
|
|
4
|
+
import { dirname, join, relative, resolve, sep } from "node:path";
|
|
5
|
+
import { formatDiagnostic, transform } from "@reckona/mreact-compiler";
|
|
9
6
|
import type {
|
|
10
7
|
ClientReferenceMetadata,
|
|
11
8
|
ServerOutputMode,
|
|
@@ -178,10 +175,9 @@ export interface RenderAppRequestOptions {
|
|
|
178
175
|
serverModuleCacheVersion?: string | undefined;
|
|
179
176
|
serverSourceFiles?: ReadonlyMap<string, string> | undefined;
|
|
180
177
|
serverActions?: AppRouterServerActionOptions | undefined;
|
|
181
|
-
serverActionReferencesByFile?:
|
|
182
|
-
string,
|
|
183
|
-
|
|
184
|
-
> | undefined;
|
|
178
|
+
serverActionReferencesByFile?:
|
|
179
|
+
| ReadonlyMap<string, readonly PreparedFormActionReference[]>
|
|
180
|
+
| undefined;
|
|
185
181
|
skipMiddleware?: boolean | undefined;
|
|
186
182
|
preload?: AppRouterRenderPreload | undefined;
|
|
187
183
|
vitePlugins?: readonly PluginOption[] | undefined;
|
|
@@ -853,6 +849,7 @@ async function renderAppRequestInternal(options: RenderAppRequestOptions): Promi
|
|
|
853
849
|
return await dispatchServerRoute({
|
|
854
850
|
env: options.env,
|
|
855
851
|
file: matched.route.file,
|
|
852
|
+
importPolicy: options.importPolicy,
|
|
856
853
|
params: matched.params,
|
|
857
854
|
request: options.request,
|
|
858
855
|
route: matched.route,
|
|
@@ -914,12 +911,13 @@ async function renderAppRequestInternal(options: RenderAppRequestOptions): Promi
|
|
|
914
911
|
: cachePolicy.revalidateSeconds !== 0;
|
|
915
912
|
const reloadRouteCache = isNavigationRouteCacheReloadRequest(options.request);
|
|
916
913
|
phaseStartedAt = renderTimingPhaseStartedAt(timing);
|
|
917
|
-
const cachedResponse =
|
|
918
|
-
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
|
|
914
|
+
const cachedResponse =
|
|
915
|
+
!mayUseRouteCache || reloadRouteCache
|
|
916
|
+
? undefined
|
|
917
|
+
: await cachedRouteResponse({
|
|
918
|
+
cache: options.routeCache,
|
|
919
|
+
key: cacheKey,
|
|
920
|
+
});
|
|
923
921
|
finishRenderTimingPhase(timing, phaseStartedAt, "routeCacheMs");
|
|
924
922
|
|
|
925
923
|
if (cachedResponse !== undefined) {
|
|
@@ -1595,7 +1593,9 @@ function isNavigationRequest(request: Request): boolean {
|
|
|
1595
1593
|
}
|
|
1596
1594
|
|
|
1597
1595
|
function isNavigationRouteCacheReloadRequest(request: Request): boolean {
|
|
1598
|
-
return
|
|
1596
|
+
return (
|
|
1597
|
+
isNavigationRequest(request) && request.headers.get("x-mreact-navigation-cache") === "reload"
|
|
1598
|
+
);
|
|
1599
1599
|
}
|
|
1600
1600
|
|
|
1601
1601
|
async function nearestBoundaryFileForPage(options: {
|
|
@@ -1858,6 +1858,7 @@ function errorDebugContext(
|
|
|
1858
1858
|
async function dispatchServerRoute(options: {
|
|
1859
1859
|
env?: unknown;
|
|
1860
1860
|
file: string;
|
|
1861
|
+
importPolicy?: AppRouterImportPolicy | undefined;
|
|
1861
1862
|
params: RouteParams;
|
|
1862
1863
|
request: Request;
|
|
1863
1864
|
route: AppRoute;
|
|
@@ -1992,17 +1993,15 @@ async function dispatchMetadataRoute(options: {
|
|
|
1992
1993
|
value instanceof Uint8Array
|
|
1993
1994
|
? value
|
|
1994
1995
|
: new TextEncoder().encode(typeof value === "string" ? value : String(value));
|
|
1995
|
-
return bytesResponse(
|
|
1996
|
-
|
|
1997
|
-
|
|
1998
|
-
|
|
1999
|
-
"
|
|
2000
|
-
"content-type": typeof value === "string" && value.trimStart().startsWith("<svg")
|
|
1996
|
+
return bytesResponse(body, {
|
|
1997
|
+
headers: {
|
|
1998
|
+
"cache-control": "public, max-age=3600",
|
|
1999
|
+
"content-type":
|
|
2000
|
+
typeof value === "string" && value.trimStart().startsWith("<svg")
|
|
2001
2001
|
? "image/svg+xml"
|
|
2002
2002
|
: "application/octet-stream",
|
|
2003
|
-
},
|
|
2004
2003
|
},
|
|
2005
|
-
);
|
|
2004
|
+
});
|
|
2006
2005
|
}
|
|
2007
2006
|
|
|
2008
2007
|
return new Response("Invalid metadata route convention", { status: 500 });
|
|
@@ -2010,23 +2009,27 @@ async function dispatchMetadataRoute(options: {
|
|
|
2010
2009
|
|
|
2011
2010
|
async function loadServerRouteModule(options: {
|
|
2012
2011
|
file: string;
|
|
2012
|
+
importPolicy?: AppRouterImportPolicy | undefined;
|
|
2013
2013
|
serverModules?: ReadonlyMap<string, BuiltServerModuleArtifact> | undefined;
|
|
2014
2014
|
serverModuleCacheVersion?: string | undefined;
|
|
2015
2015
|
serverSourceFiles?: ReadonlyMap<string, string> | undefined;
|
|
2016
2016
|
vitePlugins?: readonly PluginOption[] | undefined;
|
|
2017
2017
|
}): Promise<Record<string, unknown>> {
|
|
2018
|
+
const code = await readServerSourceFile(
|
|
2019
|
+
options.file,
|
|
2020
|
+
options.serverModuleCacheVersion,
|
|
2021
|
+
options.serverSourceFiles,
|
|
2022
|
+
);
|
|
2023
|
+
const externalSourceDirs = devExternalSourceDirs(options.file, options.importPolicy);
|
|
2024
|
+
|
|
2018
2025
|
if (
|
|
2019
2026
|
options.serverModuleCacheVersion === undefined &&
|
|
2020
|
-
(options.vitePlugins === undefined || options.vitePlugins.length === 0)
|
|
2027
|
+
(options.vitePlugins === undefined || options.vitePlugins.length === 0) &&
|
|
2028
|
+
(externalSourceDirs === undefined || !hasRelativeSourceImport(code))
|
|
2021
2029
|
) {
|
|
2022
2030
|
return await importAppRouterFileModule<Record<string, unknown>>(options.file);
|
|
2023
2031
|
}
|
|
2024
2032
|
|
|
2025
|
-
const code = await readServerSourceFile(
|
|
2026
|
-
options.file,
|
|
2027
|
-
options.serverModuleCacheVersion,
|
|
2028
|
-
options.serverSourceFiles,
|
|
2029
|
-
);
|
|
2030
2033
|
const artifactCode = options.serverModules?.get(options.file)?.request;
|
|
2031
2034
|
const codeHash = memoizedHashText(code);
|
|
2032
2035
|
if (
|
|
@@ -2057,6 +2060,7 @@ async function loadServerRouteModule(options: {
|
|
|
2057
2060
|
const loaded = importAppRouterSourceModule<Record<string, unknown>>({
|
|
2058
2061
|
cacheKey,
|
|
2059
2062
|
code: moduleCode,
|
|
2063
|
+
externalizeAppSourceModuleDirs: externalSourceDirs,
|
|
2060
2064
|
label: `server-route:${options.file}`,
|
|
2061
2065
|
...(moduleCode === code ? { resolveDir: dirname(options.file) } : {}),
|
|
2062
2066
|
sourcefile: options.file,
|
|
@@ -2076,6 +2080,25 @@ async function loadServerRouteModule(options: {
|
|
|
2076
2080
|
return loaded;
|
|
2077
2081
|
}
|
|
2078
2082
|
|
|
2083
|
+
function hasRelativeSourceImport(code: string): boolean {
|
|
2084
|
+
return (
|
|
2085
|
+
/\b(?:import|export)\s+(?:[^"'()]*?\s+from\s+)?["']\.{1,2}\//u.test(code) ||
|
|
2086
|
+
/\bimport\s*\(\s*["']\.{1,2}\//u.test(code)
|
|
2087
|
+
);
|
|
2088
|
+
}
|
|
2089
|
+
|
|
2090
|
+
function devExternalSourceDirs(
|
|
2091
|
+
baseDir: string,
|
|
2092
|
+
importPolicy: AppRouterImportPolicy | undefined,
|
|
2093
|
+
): readonly string[] | undefined {
|
|
2094
|
+
if (importPolicy?.allowedSourceDirs === undefined) {
|
|
2095
|
+
return undefined;
|
|
2096
|
+
}
|
|
2097
|
+
|
|
2098
|
+
const projectRoot = resolve(importPolicy.projectRoot ?? baseDir);
|
|
2099
|
+
return importPolicy.allowedSourceDirs.map((directory) => resolve(projectRoot, directory));
|
|
2100
|
+
}
|
|
2101
|
+
|
|
2079
2102
|
async function runMiddleware(options: {
|
|
2080
2103
|
appDir: string;
|
|
2081
2104
|
importPolicy?: AppRouterImportPolicy | undefined;
|
|
@@ -3871,12 +3894,14 @@ async function loadRouteLoaderModule(options: {
|
|
|
3871
3894
|
export async function bundleRouteLoaderModuleCode(options: {
|
|
3872
3895
|
appDir: string;
|
|
3873
3896
|
code: string;
|
|
3897
|
+
externalizeAppSourceModuleDirs?: readonly string[] | undefined;
|
|
3874
3898
|
filename: string;
|
|
3875
3899
|
importPolicy?: AppRouterImportPolicy | undefined;
|
|
3876
3900
|
vitePlugins?: readonly PluginOption[] | undefined;
|
|
3877
3901
|
}): Promise<string> {
|
|
3878
3902
|
const output = await bundleRouterModule({
|
|
3879
3903
|
code: stripRouteLoaderOnlyExports(options.code),
|
|
3904
|
+
externalizeAppSourceModuleDirs: options.externalizeAppSourceModuleDirs,
|
|
3880
3905
|
filename: options.filename,
|
|
3881
3906
|
platform: "node",
|
|
3882
3907
|
vitePlugins: options.vitePlugins,
|
|
@@ -3920,6 +3945,10 @@ async function loadBundledRouteLoaderModule(options: {
|
|
|
3920
3945
|
(await bundleRouteLoaderModuleCode({
|
|
3921
3946
|
appDir: options.appDir,
|
|
3922
3947
|
code: options.code,
|
|
3948
|
+
externalizeAppSourceModuleDirs:
|
|
3949
|
+
options.serverModuleCacheVersion === undefined
|
|
3950
|
+
? devExternalSourceDirs(options.appDir, options.importPolicy)
|
|
3951
|
+
: undefined,
|
|
3923
3952
|
filename: options.filename,
|
|
3924
3953
|
importPolicy: options.importPolicy,
|
|
3925
3954
|
vitePlugins: options.vitePlugins,
|
package/src/vite.ts
CHANGED
|
@@ -6,7 +6,13 @@ import {
|
|
|
6
6
|
createCompilerModuleContext,
|
|
7
7
|
transformCompilerModuleContext,
|
|
8
8
|
} from "@reckona/mreact-compiler/internal";
|
|
9
|
-
import {
|
|
9
|
+
import {
|
|
10
|
+
normalizePath,
|
|
11
|
+
type Connect,
|
|
12
|
+
type Plugin,
|
|
13
|
+
type PluginOption,
|
|
14
|
+
type ViteDevServer,
|
|
15
|
+
} from "vite";
|
|
10
16
|
import type { AppRouterServerActionOptions } from "./actions.js";
|
|
11
17
|
import type { AppRouterCache } from "./cache.js";
|
|
12
18
|
import {
|
|
@@ -69,11 +75,11 @@ type MreactRouterPlugin = Plugin & {
|
|
|
69
75
|
[mreactRouterConfigKey]: ResolvedAppRouterProject;
|
|
70
76
|
};
|
|
71
77
|
|
|
72
|
-
export function createAppRouterVitePlugin(
|
|
73
|
-
options: AppRouterVitePluginOptions,
|
|
74
|
-
): Plugin {
|
|
78
|
+
export function createAppRouterVitePlugin(options: AppRouterVitePluginOptions): Plugin {
|
|
75
79
|
const project = resolveAppRouterProjectOptions(options);
|
|
76
|
-
const normalizedSourceDirs = project.allowedSourceDirs.map((directory) =>
|
|
80
|
+
const normalizedSourceDirs = project.allowedSourceDirs.map((directory) =>
|
|
81
|
+
normalizePath(directory),
|
|
82
|
+
);
|
|
77
83
|
const packageFile = (monorepoDir: string, packageName: string, entry: string): string =>
|
|
78
84
|
workspacePackageFile({
|
|
79
85
|
currentFileUrl: import.meta.url,
|
|
@@ -94,18 +100,21 @@ export function createAppRouterVitePlugin(
|
|
|
94
100
|
"@reckona/mreact-compat",
|
|
95
101
|
];
|
|
96
102
|
const runtimePaths = new Map([
|
|
103
|
+
["react", reactCompatPath],
|
|
104
|
+
["react-dom", reactCompatPath],
|
|
105
|
+
["react-dom/client", reactCompatPath],
|
|
106
|
+
["react-dom/server", reactCompatPath],
|
|
97
107
|
[
|
|
98
|
-
"
|
|
99
|
-
packageFile("
|
|
100
|
-
],
|
|
101
|
-
[
|
|
102
|
-
"@reckona/mreact-reactive-dom",
|
|
103
|
-
reactiveDomPath,
|
|
108
|
+
"react/jsx-dev-runtime",
|
|
109
|
+
packageFile("react-compat", "@reckona/mreact-compat", "jsx-dev-runtime"),
|
|
104
110
|
],
|
|
111
|
+
["react/jsx-runtime", packageFile("react-compat", "@reckona/mreact-compat", "jsx-runtime")],
|
|
105
112
|
[
|
|
106
|
-
"@reckona/mreact-
|
|
107
|
-
|
|
113
|
+
"@reckona/mreact-reactive-core/internal",
|
|
114
|
+
packageFile("reactive-core", "@reckona/mreact-reactive-core", "internal"),
|
|
108
115
|
],
|
|
116
|
+
["@reckona/mreact-reactive-dom", reactiveDomPath],
|
|
117
|
+
["@reckona/mreact-compat", reactCompatPath],
|
|
109
118
|
[
|
|
110
119
|
"@reckona/mreact-compat/event-priority",
|
|
111
120
|
packageFile("react-compat", "@reckona/mreact-compat", "event-priority"),
|
|
@@ -130,10 +139,7 @@ export function createAppRouterVitePlugin(
|
|
|
130
139
|
"@reckona/mreact-compat/scheduler",
|
|
131
140
|
packageFile("react-compat", "@reckona/mreact-compat", "scheduler"),
|
|
132
141
|
],
|
|
133
|
-
[
|
|
134
|
-
"@reckona/mreact-router/link",
|
|
135
|
-
packageFile("router", "@reckona/mreact-router", "link"),
|
|
136
|
-
],
|
|
142
|
+
["@reckona/mreact-router/link", packageFile("router", "@reckona/mreact-router", "link")],
|
|
137
143
|
[
|
|
138
144
|
"@reckona/mreact-router/navigation-state",
|
|
139
145
|
packageFile("router", "@reckona/mreact-router", "navigation-state"),
|
|
@@ -158,9 +164,7 @@ export function createAppRouterVitePlugin(
|
|
|
158
164
|
vitePlugins: server.config.plugins,
|
|
159
165
|
};
|
|
160
166
|
|
|
161
|
-
server.middlewares.use(
|
|
162
|
-
createAppRouterViteMiddleware(middlewareOptions),
|
|
163
|
-
);
|
|
167
|
+
server.middlewares.use(createAppRouterViteMiddleware(middlewareOptions));
|
|
164
168
|
};
|
|
165
169
|
},
|
|
166
170
|
handleHotUpdate(context) {
|
|
@@ -207,11 +211,9 @@ export function currentDevtoolsEmitter() { return undefined; }`;
|
|
|
207
211
|
}
|
|
208
212
|
|
|
209
213
|
if (id.startsWith(virtualClientPrefix)) {
|
|
210
|
-
return renderAppRouterClientAsset(
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
{ dev: true },
|
|
214
|
-
).then(async (response) => {
|
|
214
|
+
return renderAppRouterClientAsset(project.routesDir, id.slice(virtualClientPrefix.length), {
|
|
215
|
+
dev: true,
|
|
216
|
+
}).then(async (response) => {
|
|
215
217
|
if (!response.ok) {
|
|
216
218
|
const message = await response.text();
|
|
217
219
|
throw new Error(message || `MReact client route asset was not found: ${id}`);
|
|
@@ -259,9 +261,7 @@ export function currentDevtoolsEmitter() { return undefined; }`;
|
|
|
259
261
|
|
|
260
262
|
if (output.diagnostics.length > 0) {
|
|
261
263
|
throw new Error(
|
|
262
|
-
output.diagnostics
|
|
263
|
-
.map((diagnostic) => formatDiagnostic(filename, diagnostic))
|
|
264
|
-
.join("\n"),
|
|
264
|
+
output.diagnostics.map((diagnostic) => formatDiagnostic(filename, diagnostic)).join("\n"),
|
|
265
265
|
);
|
|
266
266
|
}
|
|
267
267
|
|
|
@@ -336,11 +336,7 @@ export function mreactRouterConfigFromPlugins(
|
|
|
336
336
|
plugins: readonly unknown[],
|
|
337
337
|
): ResolvedAppRouterProject | undefined {
|
|
338
338
|
for (const plugin of plugins.flat(Infinity)) {
|
|
339
|
-
if (
|
|
340
|
-
plugin !== null &&
|
|
341
|
-
typeof plugin === "object" &&
|
|
342
|
-
mreactRouterConfigKey in plugin
|
|
343
|
-
) {
|
|
339
|
+
if (plugin !== null && typeof plugin === "object" && mreactRouterConfigKey in plugin) {
|
|
344
340
|
return (plugin as MreactRouterPlugin)[mreactRouterConfigKey];
|
|
345
341
|
}
|
|
346
342
|
}
|
|
@@ -602,9 +598,7 @@ function importerInRuntimePackage(
|
|
|
602
598
|
const normalizedImporter = normalizePath(importer);
|
|
603
599
|
return (
|
|
604
600
|
directories.some((directory) => normalizedImporter.startsWith(`${directory}/`)) ||
|
|
605
|
-
packageNames.some((packageName) =>
|
|
606
|
-
normalizedImporter.includes(`/node_modules/${packageName}/`),
|
|
607
|
-
)
|
|
601
|
+
packageNames.some((packageName) => normalizedImporter.includes(`/node_modules/${packageName}/`))
|
|
608
602
|
);
|
|
609
603
|
}
|
|
610
604
|
|
|
@@ -661,7 +655,9 @@ async function devNavigationScripts(appDir: string): Promise<ReadonlyMap<string,
|
|
|
661
655
|
}),
|
|
662
656
|
);
|
|
663
657
|
|
|
664
|
-
return new Map(
|
|
658
|
+
return new Map(
|
|
659
|
+
entries.filter((entry): entry is readonly [string, string] => entry !== undefined),
|
|
660
|
+
);
|
|
665
661
|
}
|
|
666
662
|
|
|
667
663
|
function createDevCssProxyMiddleware(): Connect.NextHandleFunction {
|