@reckona/mreact-router 0.0.135 → 0.0.136
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 +1 -1
- package/dist/client.d.ts.map +1 -1
- package/dist/client.js +19 -6
- package/dist/client.js.map +1 -1
- package/package.json +11 -11
- package/src/client.ts +21 -5
package/README.md
CHANGED
|
@@ -116,7 +116,7 @@ Plain `multipart/form-data` route handlers do not automatically run the server-a
|
|
|
116
116
|
|
|
117
117
|
Use `startDevServer()` and `startServer()` when an app needs to attach HTTP upgrade handling to the same Node server as mreact routes. Both APIs accept `onUpgrade(request, socket, head)`, and `startDevServer()` keeps Vite middleware/HMR wired to the underlying server. Production route artifacts are bundled independently, so mutable custom-server state should live in `getServerRuntimeState(key, create)` rather than in a module-scoped `let` singleton.
|
|
118
118
|
|
|
119
|
-
Client boundary markers have the same SSR behavior. A plain `Foo.tsx` component runs on the server and does not hydrate by itself. Marking a component boundary with either `Foo.client.tsx` or a top-level `"use client";` directive makes that boundary hydrate on the client; SSR emits a `<template data-mreact-client-boundary="...">` placeholder plus serialized props, and the component JSX appears after hydration. When a client boundary wrapper receives server-renderable JSX children, those children remain visible as SSR DOM between the boundary marker and its props payload so the initial response stays paintable and indexable before hydration. Inferred boundaries from plain imported components can also keep an SSR fallback when
|
|
119
|
+
Client boundary markers have the same SSR behavior. A plain `Foo.tsx` component runs on the server and does not hydrate by itself. Marking a component boundary with either `Foo.client.tsx` or a top-level `"use client";` directive makes that boundary hydrate on the client; SSR emits a `<template data-mreact-client-boundary="...">` placeholder plus serialized props, and the component JSX appears after hydration. When a client boundary wrapper receives server-renderable JSX children, those children remain visible as SSR DOM between the boundary marker and its props payload so the initial response stays paintable and indexable before hydration. Inferred boundaries from plain imported components can also keep an SSR fallback when every browser-global read is guarded by a `typeof window !== "undefined"` style check: a guarded if/ternary branch, a short-circuited logical expression, or statements after a guarded early exit such as `if (typeof window === "undefined") return;`. A guard on one of `window`, `document`, or `localStorage` covers the others. Unguarded reads, and guards the analyzer cannot follow such as an aliased `const isBrowser = typeof window !== "undefined"` condition, still disable fallback eligibility and produce a placeholder-only boundary. Combining `.client.tsx` with `"use client";` is redundant and does not change the boundary behavior. Route-level `"use client";` is separate: when it appears in a page, layout, or template route module, the whole route is emitted as a hydrated client route. In development, app-local client boundary dependencies are transformed through the mreact client compiler before Vite serves them, and generated mreact runtime imports are resolved by the router plugin, so server-rendered layouts and app shells can import hydrated client controls without adding React or mreact compat runtime aliases.
|
|
120
120
|
|
|
121
121
|
Hydrated route scripts set `data-mreact-hydrated="true"` on both the route marker and `document.documentElement`, then dispatch a `mreact:hydrated` event with `{ routeId }` in `event.detail`. Tests and app chrome can wait for that document-level signal instead of relying on unrelated UI side effects.
|
|
122
122
|
|
package/dist/client.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAIA,OAAO,EAML,KAAK,yBAAyB,EAI/B,MAAM,0BAA0B,CAAC;AAClC,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,0CAA0C,CAAC;AACxF,OAAO,
|
|
1
|
+
{"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"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"}
|
package/dist/client.js
CHANGED
|
@@ -3,7 +3,7 @@ import { readFile, stat } from "node:fs/promises";
|
|
|
3
3
|
import { builtinModules } from "node:module";
|
|
4
4
|
import { dirname, extname, join, relative, sep } from "node:path";
|
|
5
5
|
import { analyzeBoundaryGraph, collectClientRouteModuleAnalysis, formatDiagnostic, } from "@reckona/mreact-compiler";
|
|
6
|
-
import { collectClientRouteModuleAnalysisFromContext, createCompilerModuleContext, readTopLevelBooleanExport, readTopLevelBooleanExportFromContext, stripTypeScriptWithOxc, transformCompilerModuleContext, } from "@reckona/mreact-compiler/internal";
|
|
6
|
+
import { collectClientRouteModuleAnalysisFromContext, createCompilerModuleContext, hasUnguardedBrowserGlobalReference, readTopLevelBooleanExport, readTopLevelBooleanExportFromContext, stripTypeScriptWithOxc, transformCompilerModuleContext, } from "@reckona/mreact-compiler/internal";
|
|
7
7
|
import { assetPath } from "./assets.js";
|
|
8
8
|
import { bundleRouterModule, bundleRouterModules, } from "./bundle-pipeline.js";
|
|
9
9
|
import { resolveClientConsolePureFunctions } from "./config.js";
|
|
@@ -515,7 +515,8 @@ async function inferClientRouteModuleSource(options) {
|
|
|
515
515
|
continue;
|
|
516
516
|
}
|
|
517
517
|
clientBoundaryImports.push(reference.source);
|
|
518
|
-
if (!imported.clientBoundaryModule &&
|
|
518
|
+
if (!imported.clientBoundaryModule &&
|
|
519
|
+
isClientBoundaryFallbackEligibleSource(source, resolved)) {
|
|
519
520
|
clientBoundaryFallbackImports.push(reference.source);
|
|
520
521
|
}
|
|
521
522
|
continue;
|
|
@@ -712,8 +713,8 @@ function isStyleModuleSpecifier(source) {
|
|
|
712
713
|
return styleModuleExtensions.has(extname(pathname));
|
|
713
714
|
}
|
|
714
715
|
const styleModuleExtensions = new Set([".css", ".less", ".sass", ".scss", ".styl", ".stylus"]);
|
|
715
|
-
function isClientBoundaryFallbackEligibleSource(source) {
|
|
716
|
-
if (hasClientBoundaryFallbackUnsafeBrowserGlobal(source)) {
|
|
716
|
+
function isClientBoundaryFallbackEligibleSource(source, filename) {
|
|
717
|
+
if (hasClientBoundaryFallbackUnsafeBrowserGlobal(source, filename)) {
|
|
717
718
|
return false;
|
|
718
719
|
}
|
|
719
720
|
const destructuredCallbackPropNames = destructuredPropsCallbackNames(source);
|
|
@@ -750,9 +751,21 @@ function isClientBoundaryFallbackEligibleSource(source) {
|
|
|
750
751
|
return (!/\bon[A-Z][A-Za-z0-9_$]*\s*=/u.test(sourceWithoutGuardedUndefinedCallbacks) &&
|
|
751
752
|
!/\bglobalThis\b/u.test(source));
|
|
752
753
|
}
|
|
753
|
-
function hasClientBoundaryFallbackUnsafeBrowserGlobal(source) {
|
|
754
|
+
function hasClientBoundaryFallbackUnsafeBrowserGlobal(source, filename) {
|
|
754
755
|
const sourceWithoutTypeofGuards = source.replaceAll(/\btypeof\s+(?:window|document|localStorage)\s*(?:(?:={2,3}|!={1,2})\s*["']undefined["'])?/gu, "");
|
|
755
|
-
|
|
756
|
+
if (!/\b(?:window|document|localStorage)\b/u.test(sourceWithoutTypeofGuards)) {
|
|
757
|
+
return false;
|
|
758
|
+
}
|
|
759
|
+
// Remaining browser-global tokens may still be typeof-guarded uses such as
|
|
760
|
+
// `if (typeof window !== "undefined") return window.location.pathname;`.
|
|
761
|
+
// Those never execute on the server, so the AST guard analysis decides;
|
|
762
|
+
// an unparsable module stays conservatively ineligible.
|
|
763
|
+
try {
|
|
764
|
+
return hasUnguardedBrowserGlobalReference({ code: source, filename });
|
|
765
|
+
}
|
|
766
|
+
catch {
|
|
767
|
+
return true;
|
|
768
|
+
}
|
|
756
769
|
}
|
|
757
770
|
function propsCallbackAliasNames(source) {
|
|
758
771
|
const names = new Set();
|