@webtypen/webframez-react 0.0.35 → 0.0.36
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/bin/webframez-react.mjs +358 -1
- package/defaults/default-client.js +3 -0
- package/defaults/webpack.client.cjs +177 -10
- package/dist/build-plugin.cjs +111 -0
- package/dist/build-plugin.d.ts +14 -0
- package/dist/build-plugin.js +77 -0
- package/dist/client.cjs +1 -1
- package/dist/client.js +1 -1
- package/dist/http.cjs +197 -35
- package/dist/http.js +202 -35
- package/dist/index.cjs +325 -51
- package/dist/index.js +327 -51
- package/dist/types.d.ts +0 -1
- package/dist/webframez-core.cjs +325 -51
- package/dist/webframez-core.d.ts +27 -3
- package/dist/webframez-core.js +329 -51
- package/package.json +10 -1
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
var __create = Object.create;
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
|
+
var __getProtoOf = Object.getPrototypeOf;
|
|
6
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
7
|
+
var __export = (target, all) => {
|
|
8
|
+
for (var name in all)
|
|
9
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
10
|
+
};
|
|
11
|
+
var __copyProps = (to, from, except, desc) => {
|
|
12
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
13
|
+
for (let key of __getOwnPropNames(from))
|
|
14
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
15
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
16
|
+
}
|
|
17
|
+
return to;
|
|
18
|
+
};
|
|
19
|
+
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
|
|
20
|
+
// If the importer is in node compatibility mode or this is not an ESM
|
|
21
|
+
// file that has been converted to a CommonJS file using a Babel-
|
|
22
|
+
// compatible transform (i.e. "__esModule" has not been set), then set
|
|
23
|
+
// "default" to the CommonJS "module.exports" for node compatibility.
|
|
24
|
+
isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
|
|
25
|
+
mod
|
|
26
|
+
));
|
|
27
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
28
|
+
|
|
29
|
+
// src/build-plugin.ts
|
|
30
|
+
var build_plugin_exports = {};
|
|
31
|
+
__export(build_plugin_exports, {
|
|
32
|
+
createPlugin: () => createPlugin,
|
|
33
|
+
default: () => build_plugin_default
|
|
34
|
+
});
|
|
35
|
+
module.exports = __toCommonJS(build_plugin_exports);
|
|
36
|
+
var import_node_fs = __toESM(require("node:fs"), 1);
|
|
37
|
+
var import_node_path = __toESM(require("node:path"), 1);
|
|
38
|
+
function fileExists(filePath) {
|
|
39
|
+
return import_node_fs.default.existsSync(filePath);
|
|
40
|
+
}
|
|
41
|
+
function readJson(filePath) {
|
|
42
|
+
return JSON.parse(import_node_fs.default.readFileSync(filePath, "utf-8"));
|
|
43
|
+
}
|
|
44
|
+
function collectManifestChunks(manifestPath) {
|
|
45
|
+
const manifest = readJson(manifestPath);
|
|
46
|
+
const chunks = /* @__PURE__ */ new Set();
|
|
47
|
+
for (const value of Object.values(manifest)) {
|
|
48
|
+
const entry = value;
|
|
49
|
+
if (!entry || !Array.isArray(entry.chunks)) {
|
|
50
|
+
continue;
|
|
51
|
+
}
|
|
52
|
+
for (const chunk of entry.chunks) {
|
|
53
|
+
if (typeof chunk === "string" && chunk.includes(".")) {
|
|
54
|
+
chunks.add(chunk);
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
return chunks;
|
|
59
|
+
}
|
|
60
|
+
function validateRouteDist(distRootDir) {
|
|
61
|
+
const requiredFiles = ["client.js", "react-client-manifest.json", "react-ssr-manifest.json"];
|
|
62
|
+
for (const requiredFile of requiredFiles) {
|
|
63
|
+
const filePath = import_node_path.default.join(distRootDir, requiredFile);
|
|
64
|
+
if (!fileExists(filePath)) {
|
|
65
|
+
throw new Error(`webframez-react build output missing: ${filePath}`);
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
for (const chunk of collectManifestChunks(import_node_path.default.join(distRootDir, "react-client-manifest.json"))) {
|
|
69
|
+
const chunkPath = import_node_path.default.join(distRootDir, chunk);
|
|
70
|
+
if (!fileExists(chunkPath)) {
|
|
71
|
+
throw new Error(`webframez-react manifest references missing chunk: ${chunkPath}`);
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
function findReactRouteDistRoots(stagingDir) {
|
|
76
|
+
const reactRoot = import_node_path.default.join(stagingDir, "webframez-react");
|
|
77
|
+
if (!fileExists(reactRoot)) {
|
|
78
|
+
return [];
|
|
79
|
+
}
|
|
80
|
+
return import_node_fs.default.readdirSync(reactRoot, { withFileTypes: true }).filter((entry) => entry.isDirectory()).map((entry) => import_node_path.default.join(reactRoot, entry.name));
|
|
81
|
+
}
|
|
82
|
+
function createPlugin() {
|
|
83
|
+
return {
|
|
84
|
+
name: "webframez-react",
|
|
85
|
+
async buildAssets(context) {
|
|
86
|
+
const routesPath = import_node_path.default.join(context.stagingDir, "app", "routes.js");
|
|
87
|
+
if (!fileExists(routesPath)) {
|
|
88
|
+
return;
|
|
89
|
+
}
|
|
90
|
+
const code = await context.run("webframez-react", [
|
|
91
|
+
"build:routes",
|
|
92
|
+
`--routes=${routesPath}`,
|
|
93
|
+
`--out-dir=${context.stagingDir}`,
|
|
94
|
+
`--runtime-out-dir=${context.outDir}`
|
|
95
|
+
]);
|
|
96
|
+
if (code !== 0) {
|
|
97
|
+
throw new Error(`webframez-react build failed with code ${code}`);
|
|
98
|
+
}
|
|
99
|
+
},
|
|
100
|
+
validateBuild(context) {
|
|
101
|
+
for (const distRootDir of findReactRouteDistRoots(context.stagingDir)) {
|
|
102
|
+
validateRouteDist(distRootDir);
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
};
|
|
106
|
+
}
|
|
107
|
+
var build_plugin_default = createPlugin;
|
|
108
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
109
|
+
0 && (module.exports = {
|
|
110
|
+
createPlugin
|
|
111
|
+
});
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export type WebframezBuildContext = {
|
|
2
|
+
projectRoot: string;
|
|
3
|
+
stagingDir: string;
|
|
4
|
+
outDir: string;
|
|
5
|
+
run: (binaryName: string, args: string[], envAdditions?: Record<string, string>) => Promise<number>;
|
|
6
|
+
};
|
|
7
|
+
|
|
8
|
+
export declare function createPlugin(): {
|
|
9
|
+
name: string;
|
|
10
|
+
buildAssets(context: WebframezBuildContext): Promise<void>;
|
|
11
|
+
validateBuild(context: WebframezBuildContext): void;
|
|
12
|
+
};
|
|
13
|
+
|
|
14
|
+
export default createPlugin;
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
// src/build-plugin.ts
|
|
2
|
+
import fs from "node:fs";
|
|
3
|
+
import path from "node:path";
|
|
4
|
+
function fileExists(filePath) {
|
|
5
|
+
return fs.existsSync(filePath);
|
|
6
|
+
}
|
|
7
|
+
function readJson(filePath) {
|
|
8
|
+
return JSON.parse(fs.readFileSync(filePath, "utf-8"));
|
|
9
|
+
}
|
|
10
|
+
function collectManifestChunks(manifestPath) {
|
|
11
|
+
const manifest = readJson(manifestPath);
|
|
12
|
+
const chunks = /* @__PURE__ */ new Set();
|
|
13
|
+
for (const value of Object.values(manifest)) {
|
|
14
|
+
const entry = value;
|
|
15
|
+
if (!entry || !Array.isArray(entry.chunks)) {
|
|
16
|
+
continue;
|
|
17
|
+
}
|
|
18
|
+
for (const chunk of entry.chunks) {
|
|
19
|
+
if (typeof chunk === "string" && chunk.includes(".")) {
|
|
20
|
+
chunks.add(chunk);
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
return chunks;
|
|
25
|
+
}
|
|
26
|
+
function validateRouteDist(distRootDir) {
|
|
27
|
+
const requiredFiles = ["client.js", "react-client-manifest.json", "react-ssr-manifest.json"];
|
|
28
|
+
for (const requiredFile of requiredFiles) {
|
|
29
|
+
const filePath = path.join(distRootDir, requiredFile);
|
|
30
|
+
if (!fileExists(filePath)) {
|
|
31
|
+
throw new Error(`webframez-react build output missing: ${filePath}`);
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
for (const chunk of collectManifestChunks(path.join(distRootDir, "react-client-manifest.json"))) {
|
|
35
|
+
const chunkPath = path.join(distRootDir, chunk);
|
|
36
|
+
if (!fileExists(chunkPath)) {
|
|
37
|
+
throw new Error(`webframez-react manifest references missing chunk: ${chunkPath}`);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
function findReactRouteDistRoots(stagingDir) {
|
|
42
|
+
const reactRoot = path.join(stagingDir, "webframez-react");
|
|
43
|
+
if (!fileExists(reactRoot)) {
|
|
44
|
+
return [];
|
|
45
|
+
}
|
|
46
|
+
return fs.readdirSync(reactRoot, { withFileTypes: true }).filter((entry) => entry.isDirectory()).map((entry) => path.join(reactRoot, entry.name));
|
|
47
|
+
}
|
|
48
|
+
function createPlugin() {
|
|
49
|
+
return {
|
|
50
|
+
name: "webframez-react",
|
|
51
|
+
async buildAssets(context) {
|
|
52
|
+
const routesPath = path.join(context.stagingDir, "app", "routes.js");
|
|
53
|
+
if (!fileExists(routesPath)) {
|
|
54
|
+
return;
|
|
55
|
+
}
|
|
56
|
+
const code = await context.run("webframez-react", [
|
|
57
|
+
"build:routes",
|
|
58
|
+
`--routes=${routesPath}`,
|
|
59
|
+
`--out-dir=${context.stagingDir}`,
|
|
60
|
+
`--runtime-out-dir=${context.outDir}`
|
|
61
|
+
]);
|
|
62
|
+
if (code !== 0) {
|
|
63
|
+
throw new Error(`webframez-react build failed with code ${code}`);
|
|
64
|
+
}
|
|
65
|
+
},
|
|
66
|
+
validateBuild(context) {
|
|
67
|
+
for (const distRootDir of findReactRouteDistRoots(context.stagingDir)) {
|
|
68
|
+
validateRouteDist(distRootDir);
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
};
|
|
72
|
+
}
|
|
73
|
+
var build_plugin_default = createPlugin;
|
|
74
|
+
export {
|
|
75
|
+
createPlugin,
|
|
76
|
+
build_plugin_default as default
|
|
77
|
+
};
|
package/dist/client.cjs
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
var se=Object.create;var y=Object.defineProperty;var ce=Object.getOwnPropertyDescriptor;var de=Object.getOwnPropertyNames;var ue=Object.getPrototypeOf,le=Object.prototype.hasOwnProperty;var fe=(e,t)=>{for(var n in t)y(e,n,{get:t[n],enumerable:!0})},L=(e,t,n,o)=>{if(t&&typeof t=="object"||typeof t=="function")for(let r of de(t))!le.call(e,r)&&r!==n&&y(e,r,{get:()=>t[r],enumerable:!(o=ce(t,r))||o.enumerable});return e};var H=(e,t,n)=>(n=e!=null?se(ue(e)):{},L(t||!e||!e.__esModule?y(n,"default",{value:e,enumerable:!0}):n,e)),pe=e=>L(y({},"__esModule",{value:!0}),e);var be={};fe(be,{mountWebframezClient:()=>ve,useCookie:()=>Ee,useRouter:()=>Ae});module.exports=pe(be);var s=H(require("react"),1),Z=require("react-dom/client"),
|
|
1
|
+
var se=Object.create;var y=Object.defineProperty;var ce=Object.getOwnPropertyDescriptor;var de=Object.getOwnPropertyNames;var ue=Object.getPrototypeOf,le=Object.prototype.hasOwnProperty;var fe=(e,t)=>{for(var n in t)y(e,n,{get:t[n],enumerable:!0})},L=(e,t,n,o)=>{if(t&&typeof t=="object"||typeof t=="function")for(let r of de(t))!le.call(e,r)&&r!==n&&y(e,r,{get:()=>t[r],enumerable:!(o=ce(t,r))||o.enumerable});return e};var H=(e,t,n)=>(n=e!=null?se(ue(e)):{},L(t||!e||!e.__esModule?y(n,"default",{value:e,enumerable:!0}):n,e)),pe=e=>L(y({},"__esModule",{value:!0}),e);var be={};fe(be,{mountWebframezClient:()=>ve,useCookie:()=>Ee,useRouter:()=>Ae});module.exports=pe(be);var s=H(require("react"),1),Z=require("react-dom/client"),R=require("react-server-dom-webpack/client"),K=require("@webtypen/webframez-react/route-slot");var me=/^(?:[a-zA-Z][a-zA-Z\d+\-.]*:|\/\/|#)/;function u(e){if(typeof e!="string")return;let t=e.trim();return!t||t==="/"?"":t.replace(/\/+$/,"")}function U(e,t){let n=e.trim(),o=u(t);return!n||!o||me.test(n)||n.startsWith("/")||o!=="/"&&(n===o||n.startsWith(`${o}/`))?n:o==="/"?n.startsWith("/")?n:`/${n}`:n.startsWith("/")?`${o}${n}`:`${o}/${n}`}function S(e,t){if(!e)return;let n=u(e.basename)??u(t),o=u(e.routeBasePath),r=u(e.transportBasePath),a={...e,...n!==void 0?{basename:n}:{},...o!==void 0?{routeBasePath:o}:{},...r!==void 0?{transportBasePath:r}:{}};return a.favicon&&(a.favicon=U(a.favicon,n)),a.links&&(a.links=a.links.map(c=>({...c,href:U(c.href,n)}))),a}var m=H(require("react"),1),$="webframez-route-children",W="__webframezRouteChildren",D="WebframezRouteChildren",N=()=>m.default.createElement($);N.displayName=D;N[W]=!0;var Re=N;function z(e){if(e===$||e===Re)return!0;if(!e||typeof e!="function"&&typeof e!="object")return!1;try{let t=e;return t[W]===!0||t.displayName===D||t.name==="RouteChildren"}catch{return!1}}function M(e){if(!e||typeof e!="object")return!1;try{return"type"in e&&"props"in e}catch{return!1}}function E(e,t){if(e==null||typeof e=="boolean")return e;if(Array.isArray(e)){let l=!1,g=e.map(p=>{let w=E(p,t);return w!==p&&(l=!0),w});return l?g:e}if(M(e)&&z(e.type))return t;let n=m.default.isValidElement(e);if(!n&&!M(e))return e;if(n&&z(e.type))return t;let o=e.props??{};if(!("children"in o))return e;let r=E(o.children,t);if(r===o.children)return e;if(n)return Array.isArray(r)?m.default.cloneElement(e,void 0,...r):m.default.cloneElement(e,void 0,r);let a=e,c={...a.props??{},children:r,...a.key!==void 0&&a.key!==null?{key:a.key}:{}};return m.default.createElement(a.type,c)}var d=require("react/jsx-runtime"),ge={push:()=>{},replace:()=>{},refresh:()=>{},refreshContext:()=>{}},A=typeof s.default.createContext=="function"?s.default.createContext(null):null,V="__WEBFRAMEZ_ROUTER__",we="[data-webframez-head='true']";function F(){if(typeof window>"u"||typeof document>"u")return;let e=()=>{window.scrollTo({top:0,left:0}),document.scrollingElement&&(document.scrollingElement.scrollTop=0),document.documentElement.scrollTop=0,document.body&&(document.body.scrollTop=0)};if(typeof window.requestAnimationFrame=="function"){window.requestAnimationFrame(e);return}window.setTimeout(e,0)}function v(e){return u(e)??""}function he(e,t){return t?e===t?"/":e.startsWith(`${t}/`)?e.slice(t.length)||"/":e||"/":e||"/"}function X(e,t){let n=!t||t==="/"?"/":t.startsWith("/")?t:`/${t}`;return e?n==="/"?e:`${e}${n}`:n}function _e(){return v(typeof window>"u"?globalThis.__RSC_ROUTE_BASE_PATH:window.__RSC_ROUTE_BASE_PATH)}function J(e){if(typeof window>"u")return e||"/";let t=v(window.__RSC_BASENAME),n=_e(),o=he(e||"/",t);return X(n,o)}function Q(e){if(typeof window>"u")return e;let t=window.__RSC_ENDPOINT;return typeof t=="string"&&t.trim()!==""?t:e}function Ce(){return typeof window>"u"?null:window[V]??null}function ye(e){typeof window>"u"||(window[V]=e)}function j(){let e={},t=typeof document>"u"?"":document.cookie;if(!t||t.trim()==="")return e;for(let n of t.split(";")){let o=n.trim();if(!o)continue;let r=o.indexOf("="),a=r>=0?o.slice(0,r).trim():o,c=r>=0?o.slice(r+1):"";a&&(e[a]=decodeURIComponent(c))}return e}function q(e,t,n={}){let o=[`${e}=${encodeURIComponent(t)}`];return n.path&&o.push(`Path=${n.path}`),n.domain&&o.push(`Domain=${n.domain}`),typeof n.maxAge=="number"&&o.push(`Max-Age=${Math.floor(n.maxAge)}`),n.expires&&o.push(`Expires=${n.expires.toUTCString()}`),n.sameSite&&o.push(`SameSite=${n.sameSite}`),n.secure&&o.push("Secure"),o.join("; ")}function Ee(){return s.default.useMemo(()=>({all:()=>j(),get:e=>j()[e],set:(e,t,n)=>{typeof document>"u"||(document.cookie=q(e,t,n))},remove:(e,t)=>{typeof document>"u"||(document.cookie=q(e,"",{...t??{},maxAge:0}))}}),[])}function Ae(){let e=A?s.default.useContext(A):null;if(!e){let t=Ce();if(t)return t;if(typeof window>"u")return ge;throw new Error("useRouter must be used inside mountWebframezClient()")}return e}function Te({active:e}){return(0,d.jsx)("div",{style:{position:"fixed",top:0,left:0,width:"100%",height:3,zIndex:9999,transformOrigin:"left",transform:e?"scaleX(1)":"scaleX(0)",transition:"transform 180ms ease",background:"linear-gradient(90deg, #0ea5e9, #22c55e)"}})}function G(e){let t=document.createElement("meta");t.setAttribute("data-webframez-head","true");let n=Object.entries(e).filter(([,o])=>!!o);for(let[o,r]of n)t.setAttribute(o,String(r));document.head.appendChild(t)}function Y(e){let t=document.createElement("link");t.setAttribute("data-webframez-head","true");let n=Object.entries(e).filter(([,o])=>!!o);for(let[o,r]of n)t.setAttribute(o,String(r));document.head.appendChild(t)}function x(e){if(typeof document>"u")return;let t=S(e)??e;ee(t),document.title=t.title||"Webframez React";for(let n of document.head.querySelectorAll(we))n.remove();t.description&&G({name:"description",content:t.description}),t.favicon&&Y({rel:"icon",href:t.favicon});for(let n of t.meta??[])G(n);for(let n of t.links??[])Y(n)}function ee(e){if(typeof window>"u")return;let t=S(e)??e,n=u(t.basename),o=u(t.routeBasePath),r=u(t.transportBasePath);window.__RSC_BASENAME=n??"",window.__RSC_ROUTE_BASE_PATH=o??"",r!==void 0&&(window.__RSC_ENDPOINT=X(r,"/rsc"))}function Pe(e){let t=new TextEncoder;return new ReadableStream({start(n){n.enqueue(t.encode(e)),n.close()}})}function Se(){if(typeof window>"u")return null;let e=window.__RSC_INITIAL_PAYLOAD;return typeof e!="string"||e===""?null:(delete window.__RSC_INITIAL_PAYLOAD,(0,R.createFromReadableStream)(Pe(e)))}function Ne(e){let t=Q(e),n=J(window.location.pathname);return Se()??(0,R.createFromFetch)(fetch(`${t}?path=${encodeURIComponent(n)}&search=${encodeURIComponent(window.location.search)}`,{cache:"no-store",credentials:"same-origin",headers:{Accept:"text/x-component"}}))}function xe(e,t){return function(){let o=s.default.use(e),r=typeof o.contextModel<"u"&&typeof o.pageModel<"u",[a,c]=(0,s.useState)(o.model),[l,g]=(0,s.useState)(o.contextModel),[p,w]=(0,s.useState)(o.pageModel),[b,I]=(0,s.useState)(o.head),[te,h]=(0,s.useState)(!1),[ne,oe]=(0,s.useState)(!1),[re,T]=(0,s.useState)(r);async function O(i){let C=Q(t),f=J(i.pathname);return await(0,R.createFromFetch)(fetch(`${C}?path=${encodeURIComponent(f)}&search=${encodeURIComponent(i.search)}`,{cache:"no-store",credentials:"same-origin",headers:{Accept:"text/x-component"}}))}async function _(i,C="push"){h(!0);try{let f=await O(i);x(f.head),I(f.head),c(f.model),g(f.contextModel),w(f.pageModel),T(!0);let P=`${i.pathname}${i.search}`;C==="replace"?(history.replaceState(null,"",P),F()):C==="push"&&(history.pushState(null,"",P),F())}catch(f){console.error("[webframez-react] Failed to render route",f),c((0,d.jsx)("p",{children:"Failed to load route."}))}finally{h(!1)}}async function ie(){h(!0);try{let i=await O(new URL(window.location.href));if(x(i.head),I(i.head),Object.prototype.hasOwnProperty.call(i,"contextModel")){g(i.contextModel),T(!0);return}c(i.model),T(!1)}catch(i){console.error("[webframez-react] Failed to refresh route context",i)}finally{h(!1)}}(0,s.useEffect)(()=>{x(b)},[b]),(0,s.useEffect)(()=>{oe(!0);let i=()=>{_(new URL(window.location.href),"none")};return window.addEventListener("popstate",i),()=>{window.removeEventListener("popstate",i)}},[]);let k=s.default.useMemo(()=>({push:i=>{_(new URL(i,window.location.origin),"push")},replace:i=>{_(new URL(i,window.location.origin),"replace")},refresh:()=>{_(new URL(window.location.href),"none")},refreshContext:()=>{ie()}}),[]);ye(k);let ae=re&&typeof p<"u"?l?(0,d.jsx)(K.RouteChildrenSlotProvider,{page:p,children:E(l,p)}):p:a,B=(0,d.jsxs)(d.Fragment,{children:[ne?(0,d.jsx)(Te,{active:te}):null,ae??(0,d.jsx)("p",{style:{padding:24},children:"Loading..."})]});return A?(0,d.jsx)(A.Provider,{value:k,children:B}):B}}function ve(e={}){let t=e.rootId??"root",n=document.getElementById(t);if(!n)throw new Error(`Missing #${t} element`);let o=typeof window<"u"&&window.__RSC_ENDPOINT,r=e.rscEndpoint??o??"/rsc",a=Promise.resolve(Ne(r)).then(l=>(l?.head&&ee(l.head),l)),c=xe(a,r);return(0,Z.hydrateRoot)(n,(0,d.jsx)(c,{}))}
|
package/dist/client.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import
|
|
1
|
+
import m,{useEffect as $,useState as f}from"react";import{hydrateRoot as ae}from"react-dom/client";import{createFromFetch as G,createFromReadableStream as se}from"react-server-dom-webpack/client";import{RouteChildrenSlotProvider as ce}from"@webtypen/webframez-react/route-slot";var re=/^(?:[a-zA-Z][a-zA-Z\d+\-.]*:|\/\/|#)/;function c(e){if(typeof e!="string")return;let t=e.trim();return!t||t==="/"?"":t.replace(/\/+$/,"")}function B(e,t){let n=e.trim(),o=c(t);return!n||!o||re.test(n)||n.startsWith("/")||o!=="/"&&(n===o||n.startsWith(`${o}/`))?n:o==="/"?n.startsWith("/")?n:`/${n}`:n.startsWith("/")?`${o}${n}`:`${o}/${n}`}function P(e,t){if(!e)return;let n=c(e.basename)??c(t),o=c(e.routeBasePath),r=c(e.transportBasePath),a={...e,...n!==void 0?{basename:n}:{},...o!==void 0?{routeBasePath:o}:{},...r!==void 0?{transportBasePath:r}:{}};return a.favicon&&(a.favicon=B(a.favicon,n)),a.links&&(a.links=a.links.map(s=>({...s,href:B(s.href,n)}))),a}import R from"react";var U="webframez-route-children",z="__webframezRouteChildren",M="WebframezRouteChildren",S=()=>R.createElement(U);S.displayName=M;S[z]=!0;var ie=S;function L(e){if(e===U||e===ie)return!0;if(!e||typeof e!="function"&&typeof e!="object")return!1;try{let t=e;return t[z]===!0||t.displayName===M||t.name==="RouteChildren"}catch{return!1}}function H(e){if(!e||typeof e!="object")return!1;try{return"type"in e&&"props"in e}catch{return!1}}function y(e,t){if(e==null||typeof e=="boolean")return e;if(Array.isArray(e)){let d=!1,g=e.map(l=>{let w=y(l,t);return w!==l&&(d=!0),w});return d?g:e}if(H(e)&&L(e.type))return t;let n=R.isValidElement(e);if(!n&&!H(e))return e;if(n&&L(e.type))return t;let o=e.props??{};if(!("children"in o))return e;let r=y(o.children,t);if(r===o.children)return e;if(n)return Array.isArray(r)?R.cloneElement(e,void 0,...r):R.cloneElement(e,void 0,r);let a=e,s={...a.props??{},children:r,...a.key!==void 0&&a.key!==null?{key:a.key}:{}};return R.createElement(a.type,s)}import{Fragment as Ce,jsx as p,jsxs as ye}from"react/jsx-runtime";var de={push:()=>{},replace:()=>{},refresh:()=>{},refreshContext:()=>{}},E=typeof m.createContext=="function"?m.createContext(null):null,Y="__WEBFRAMEZ_ROUTER__",ue="[data-webframez-head='true']";function W(){if(typeof window>"u"||typeof document>"u")return;let e=()=>{window.scrollTo({top:0,left:0}),document.scrollingElement&&(document.scrollingElement.scrollTop=0),document.documentElement.scrollTop=0,document.body&&(document.body.scrollTop=0)};if(typeof window.requestAnimationFrame=="function"){window.requestAnimationFrame(e);return}window.setTimeout(e,0)}function x(e){return c(e)??""}function le(e,t){return t?e===t?"/":e.startsWith(`${t}/`)?e.slice(t.length)||"/":e||"/":e||"/"}function Z(e,t){let n=!t||t==="/"?"/":t.startsWith("/")?t:`/${t}`;return e?n==="/"?e:`${e}${n}`:n}function fe(){return x(typeof window>"u"?globalThis.__RSC_ROUTE_BASE_PATH:window.__RSC_ROUTE_BASE_PATH)}function K(e){if(typeof window>"u")return e||"/";let t=x(window.__RSC_BASENAME),n=fe(),o=le(e||"/",t);return Z(n,o)}function V(e){if(typeof window>"u")return e;let t=window.__RSC_ENDPOINT;return typeof t=="string"&&t.trim()!==""?t:e}function pe(){return typeof window>"u"?null:window[Y]??null}function me(e){typeof window>"u"||(window[Y]=e)}function D(){let e={},t=typeof document>"u"?"":document.cookie;if(!t||t.trim()==="")return e;for(let n of t.split(";")){let o=n.trim();if(!o)continue;let r=o.indexOf("="),a=r>=0?o.slice(0,r).trim():o,s=r>=0?o.slice(r+1):"";a&&(e[a]=decodeURIComponent(s))}return e}function F(e,t,n={}){let o=[`${e}=${encodeURIComponent(t)}`];return n.path&&o.push(`Path=${n.path}`),n.domain&&o.push(`Domain=${n.domain}`),typeof n.maxAge=="number"&&o.push(`Max-Age=${Math.floor(n.maxAge)}`),n.expires&&o.push(`Expires=${n.expires.toUTCString()}`),n.sameSite&&o.push(`SameSite=${n.sameSite}`),n.secure&&o.push("Secure"),o.join("; ")}function Ie(){return m.useMemo(()=>({all:()=>D(),get:e=>D()[e],set:(e,t,n)=>{typeof document>"u"||(document.cookie=F(e,t,n))},remove:(e,t)=>{typeof document>"u"||(document.cookie=F(e,"",{...t??{},maxAge:0}))}}),[])}function Oe(){let e=E?m.useContext(E):null;if(!e){let t=pe();if(t)return t;if(typeof window>"u")return de;throw new Error("useRouter must be used inside mountWebframezClient()")}return e}function Re({active:e}){return p("div",{style:{position:"fixed",top:0,left:0,width:"100%",height:3,zIndex:9999,transformOrigin:"left",transform:e?"scaleX(1)":"scaleX(0)",transition:"transform 180ms ease",background:"linear-gradient(90deg, #0ea5e9, #22c55e)"}})}function j(e){let t=document.createElement("meta");t.setAttribute("data-webframez-head","true");let n=Object.entries(e).filter(([,o])=>!!o);for(let[o,r]of n)t.setAttribute(o,String(r));document.head.appendChild(t)}function q(e){let t=document.createElement("link");t.setAttribute("data-webframez-head","true");let n=Object.entries(e).filter(([,o])=>!!o);for(let[o,r]of n)t.setAttribute(o,String(r));document.head.appendChild(t)}function N(e){if(typeof document>"u")return;let t=P(e)??e;X(t),document.title=t.title||"Webframez React";for(let n of document.head.querySelectorAll(ue))n.remove();t.description&&j({name:"description",content:t.description}),t.favicon&&q({rel:"icon",href:t.favicon});for(let n of t.meta??[])j(n);for(let n of t.links??[])q(n)}function X(e){if(typeof window>"u")return;let t=P(e)??e,n=c(t.basename),o=c(t.routeBasePath),r=c(t.transportBasePath);window.__RSC_BASENAME=n??"",window.__RSC_ROUTE_BASE_PATH=o??"",r!==void 0&&(window.__RSC_ENDPOINT=Z(r,"/rsc"))}function ge(e){let t=new TextEncoder;return new ReadableStream({start(n){n.enqueue(t.encode(e)),n.close()}})}function we(){if(typeof window>"u")return null;let e=window.__RSC_INITIAL_PAYLOAD;return typeof e!="string"||e===""?null:(delete window.__RSC_INITIAL_PAYLOAD,se(ge(e)))}function he(e){let t=V(e),n=K(window.location.pathname);return we()??G(fetch(`${t}?path=${encodeURIComponent(n)}&search=${encodeURIComponent(window.location.search)}`,{cache:"no-store",credentials:"same-origin",headers:{Accept:"text/x-component"}}))}function _e(e,t){return function(){let o=m.use(e),r=typeof o.contextModel<"u"&&typeof o.pageModel<"u",[a,s]=f(o.model),[d,g]=f(o.contextModel),[l,w]=f(o.pageModel),[v,b]=f(o.head),[J,h]=f(!1),[Q,ee]=f(!1),[te,A]=f(r);async function I(i){let C=V(t),u=K(i.pathname);return await G(fetch(`${C}?path=${encodeURIComponent(u)}&search=${encodeURIComponent(i.search)}`,{cache:"no-store",credentials:"same-origin",headers:{Accept:"text/x-component"}}))}async function _(i,C="push"){h(!0);try{let u=await I(i);N(u.head),b(u.head),s(u.model),g(u.contextModel),w(u.pageModel),A(!0);let T=`${i.pathname}${i.search}`;C==="replace"?(history.replaceState(null,"",T),W()):C==="push"&&(history.pushState(null,"",T),W())}catch(u){console.error("[webframez-react] Failed to render route",u),s(p("p",{children:"Failed to load route."}))}finally{h(!1)}}async function ne(){h(!0);try{let i=await I(new URL(window.location.href));if(N(i.head),b(i.head),Object.prototype.hasOwnProperty.call(i,"contextModel")){g(i.contextModel),A(!0);return}s(i.model),A(!1)}catch(i){console.error("[webframez-react] Failed to refresh route context",i)}finally{h(!1)}}$(()=>{N(v)},[v]),$(()=>{ee(!0);let i=()=>{_(new URL(window.location.href),"none")};return window.addEventListener("popstate",i),()=>{window.removeEventListener("popstate",i)}},[]);let O=m.useMemo(()=>({push:i=>{_(new URL(i,window.location.origin),"push")},replace:i=>{_(new URL(i,window.location.origin),"replace")},refresh:()=>{_(new URL(window.location.href),"none")},refreshContext:()=>{ne()}}),[]);me(O);let oe=te&&typeof l<"u"?d?p(ce,{page:l,children:y(d,l)}):l:a,k=ye(Ce,{children:[Q?p(Re,{active:J}):null,oe??p("p",{style:{padding:24},children:"Loading..."})]});return E?p(E.Provider,{value:O,children:k}):k}}function ke(e={}){let t=e.rootId??"root",n=document.getElementById(t);if(!n)throw new Error(`Missing #${t} element`);let o=typeof window<"u"&&window.__RSC_ENDPOINT,r=e.rscEndpoint??o??"/rsc",a=Promise.resolve(he(r)).then(d=>(d?.head&&X(d.head),d)),s=_e(a,r);return ae(n,p(s,{}))}export{ke as mountWebframezClient,Ie as useCookie,Oe as useRouter};
|
package/dist/http.cjs
CHANGED
|
@@ -36,6 +36,7 @@ var import_node_fs2 = __toESM(require("node:fs"), 1);
|
|
|
36
36
|
var import_node_path3 = __toESM(require("node:path"), 1);
|
|
37
37
|
var import_node_url = require("node:url");
|
|
38
38
|
var import_node_child_process = require("node:child_process");
|
|
39
|
+
var import_node_zlib = require("node:zlib");
|
|
39
40
|
|
|
40
41
|
// src/server.ts
|
|
41
42
|
var import_node_path = __toESM(require("node:path"), 1);
|
|
@@ -792,7 +793,77 @@ function parseSearchParams(query) {
|
|
|
792
793
|
function createInitialHtmlErrorMarkup(message) {
|
|
793
794
|
return `<main style="font-family:system-ui,sans-serif;padding:24px"><h1 style="margin:0 0 12px">500</h1><p style="margin:0">${message}</p></main>`;
|
|
794
795
|
}
|
|
796
|
+
function createClientAssetVersion(distRootDir) {
|
|
797
|
+
try {
|
|
798
|
+
const stat = import_node_fs2.default.statSync(import_node_path3.default.join(distRootDir, "client.js"));
|
|
799
|
+
return `${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
800
|
+
} catch {
|
|
801
|
+
return "";
|
|
802
|
+
}
|
|
803
|
+
}
|
|
804
|
+
function appendAssetVersion(url, version) {
|
|
805
|
+
if (!version) {
|
|
806
|
+
return url;
|
|
807
|
+
}
|
|
808
|
+
const separator = url.includes("?") ? "&" : "?";
|
|
809
|
+
return `${url}${separator}v=${encodeURIComponent(version)}`;
|
|
810
|
+
}
|
|
811
|
+
function isWithinDirectory(filePath, directory) {
|
|
812
|
+
return filePath === directory || filePath.startsWith(`${directory}${import_node_path3.default.sep}`);
|
|
813
|
+
}
|
|
814
|
+
function isCompressibleAsset(ext) {
|
|
815
|
+
return [".js", ".mjs", ".json", ".css", ".svg", ".txt", ".html"].includes(ext);
|
|
816
|
+
}
|
|
817
|
+
function isHashedAssetPath(filePath) {
|
|
818
|
+
return /-[a-f0-9]{12,}\.[cm]?js$/i.test(import_node_path3.default.basename(filePath));
|
|
819
|
+
}
|
|
820
|
+
function setAssetContentType(res, ext) {
|
|
821
|
+
if (ext === ".js" || ext === ".mjs") {
|
|
822
|
+
res.setHeader("Content-Type", "text/javascript; charset=utf-8");
|
|
823
|
+
} else if (ext === ".json") {
|
|
824
|
+
res.setHeader("Content-Type", "application/json; charset=utf-8");
|
|
825
|
+
} else if (ext === ".css") {
|
|
826
|
+
res.setHeader("Content-Type", "text/css; charset=utf-8");
|
|
827
|
+
} else if (ext === ".svg") {
|
|
828
|
+
res.setHeader("Content-Type", "image/svg+xml; charset=utf-8");
|
|
829
|
+
}
|
|
830
|
+
}
|
|
831
|
+
function getPreferredContentEncoding(req, ext, fileSize) {
|
|
832
|
+
if (!isCompressibleAsset(ext) || fileSize < 1024) {
|
|
833
|
+
return "";
|
|
834
|
+
}
|
|
835
|
+
const acceptEncoding = String(req.headers["accept-encoding"] || "");
|
|
836
|
+
if (/\bbr\b/.test(acceptEncoding)) {
|
|
837
|
+
return "br";
|
|
838
|
+
}
|
|
839
|
+
if (/\bgzip\b/.test(acceptEncoding)) {
|
|
840
|
+
return "gzip";
|
|
841
|
+
}
|
|
842
|
+
return "";
|
|
843
|
+
}
|
|
844
|
+
function sendTextResponse(req, res, body, options) {
|
|
845
|
+
const bodyBuffer = Buffer.from(body);
|
|
846
|
+
const contentEncoding = options.compress === false ? "" : getPreferredContentEncoding(req, ".html", bodyBuffer.length);
|
|
847
|
+
res.statusCode = options.statusCode ?? 200;
|
|
848
|
+
res.setHeader("Content-Type", options.contentType);
|
|
849
|
+
if (options.cacheControl) {
|
|
850
|
+
res.setHeader("Cache-Control", options.cacheControl);
|
|
851
|
+
}
|
|
852
|
+
res.setHeader("Vary", "Accept-Encoding");
|
|
853
|
+
if (contentEncoding === "br") {
|
|
854
|
+
res.setHeader("Content-Encoding", "br");
|
|
855
|
+
res.end((0, import_node_zlib.brotliCompressSync)(bodyBuffer));
|
|
856
|
+
return;
|
|
857
|
+
}
|
|
858
|
+
if (contentEncoding === "gzip") {
|
|
859
|
+
res.setHeader("Content-Encoding", "gzip");
|
|
860
|
+
res.end((0, import_node_zlib.gzipSync)(bodyBuffer));
|
|
861
|
+
return;
|
|
862
|
+
}
|
|
863
|
+
res.end(bodyBuffer);
|
|
864
|
+
}
|
|
795
865
|
var INITIAL_HTML_WORKER_SCRIPT = `
|
|
866
|
+
const fs = require("node:fs");
|
|
796
867
|
const path = require("node:path");
|
|
797
868
|
const Module = require("node:module");
|
|
798
869
|
const { Readable, Writable } = require("node:stream");
|
|
@@ -842,11 +913,42 @@ const reactDomServer = require(path.join(path.dirname(reactDomPkg), "server.node
|
|
|
842
913
|
globalThis.__webpack_chunk_load__ = function __webframezNoopChunkLoad() {
|
|
843
914
|
return Promise.resolve();
|
|
844
915
|
};
|
|
916
|
+
function normalizeWebframezRequireCandidate(candidate) {
|
|
917
|
+
const stagingMarker = path.join(".webframez-build", "");
|
|
918
|
+
const appMarker = path.join("app", "");
|
|
919
|
+
const stagingIndex = candidate.indexOf(stagingMarker);
|
|
920
|
+
const appIndex = candidate.indexOf(appMarker, stagingIndex >= 0 ? stagingIndex : 0);
|
|
921
|
+
if (stagingIndex >= 0 && appIndex >= 0) {
|
|
922
|
+
const runtimeCandidate = path.resolve(process.cwd(), candidate.slice(appIndex));
|
|
923
|
+
if (fs.existsSync(runtimeCandidate)) {
|
|
924
|
+
return runtimeCandidate;
|
|
925
|
+
}
|
|
926
|
+
}
|
|
927
|
+
|
|
928
|
+
const frameworkDistDir = path.join("node_modules", "@webtypen", "webframez-react", "dist");
|
|
929
|
+
const shouldUseCjs =
|
|
930
|
+
candidate.includes(frameworkDistDir) &&
|
|
931
|
+
(candidate.endsWith(path.join("dist", "navigation.js")) ||
|
|
932
|
+
candidate.endsWith(path.join("dist", "route-slot.js")));
|
|
933
|
+
|
|
934
|
+
if (!shouldUseCjs) {
|
|
935
|
+
return candidate;
|
|
936
|
+
}
|
|
937
|
+
|
|
938
|
+
const cjsCandidate = candidate.slice(0, -3) + ".cjs";
|
|
939
|
+
return fs.existsSync(cjsCandidate) ? cjsCandidate : candidate;
|
|
940
|
+
}
|
|
941
|
+
|
|
845
942
|
globalThis.__webpack_require__ = function __webframezNodeRequire(id) {
|
|
846
943
|
if (typeof id !== "string") {
|
|
847
944
|
return require(id);
|
|
848
945
|
}
|
|
849
946
|
|
|
947
|
+
const directRequireTarget = normalizeWebframezRequireCandidate(id);
|
|
948
|
+
if (directRequireTarget !== id) {
|
|
949
|
+
return require(directRequireTarget);
|
|
950
|
+
}
|
|
951
|
+
|
|
850
952
|
if (id.startsWith("./")) {
|
|
851
953
|
const relativeId = id.slice(2);
|
|
852
954
|
const candidates = [
|
|
@@ -854,10 +956,16 @@ globalThis.__webpack_require__ = function __webframezNodeRequire(id) {
|
|
|
854
956
|
path.resolve(process.cwd(), "..", relativeId)
|
|
855
957
|
];
|
|
856
958
|
for (const candidate of candidates) {
|
|
959
|
+
const requireTarget = normalizeWebframezRequireCandidate(candidate);
|
|
857
960
|
try {
|
|
858
|
-
return require(
|
|
961
|
+
return require(requireTarget);
|
|
859
962
|
} catch (error) {
|
|
860
|
-
const missingCandidate =
|
|
963
|
+
const missingCandidate =
|
|
964
|
+
error &&
|
|
965
|
+
error.code === "MODULE_NOT_FOUND" &&
|
|
966
|
+
typeof error.message === "string" &&
|
|
967
|
+
(error.message.includes("'" + candidate + "'") ||
|
|
968
|
+
error.message.includes("'" + requireTarget + "'"));
|
|
861
969
|
if (!missingCandidate) {
|
|
862
970
|
throw error;
|
|
863
971
|
}
|
|
@@ -1079,6 +1187,14 @@ function joinRuntimeBasePath(basePath, pathname) {
|
|
|
1079
1187
|
}
|
|
1080
1188
|
return normalizedPath === "/" ? basePath : `${basePath}${normalizedPath}`;
|
|
1081
1189
|
}
|
|
1190
|
+
function joinRuntimeAssetPath(basePath, pathname) {
|
|
1191
|
+
const normalizedBasePath = normalizeRuntimeBasePath(basePath) ?? "";
|
|
1192
|
+
const normalizedPath = !pathname || pathname === "/" ? "/" : pathname.startsWith("/") ? pathname : `/${pathname}`;
|
|
1193
|
+
if (normalizedBasePath && (normalizedPath === normalizedBasePath || normalizedPath.startsWith(`${normalizedBasePath}/`))) {
|
|
1194
|
+
return normalizedPath;
|
|
1195
|
+
}
|
|
1196
|
+
return joinRuntimeBasePath(normalizedBasePath, normalizedPath);
|
|
1197
|
+
}
|
|
1082
1198
|
function sanitizeInitialHtmlWorkerNodeOptions(rawNodeOptions) {
|
|
1083
1199
|
if (!rawNodeOptions || rawNodeOptions.trim() === "") {
|
|
1084
1200
|
return "";
|
|
@@ -1273,6 +1389,18 @@ function createServerConsumerManifest(manifest) {
|
|
|
1273
1389
|
const consumerManifest = {};
|
|
1274
1390
|
const normalizeWorkerModuleId = (requestKey, rawModuleId) => {
|
|
1275
1391
|
if (typeof rawModuleId === "string" && rawModuleId.trim() !== "") {
|
|
1392
|
+
const isStagingModuleId = rawModuleId.startsWith("./.webframez-build/") || rawModuleId.includes(`${import_node_path3.default.sep}.webframez-build${import_node_path3.default.sep}`);
|
|
1393
|
+
const isRuntimeBuildKey = requestKey.startsWith("file://") || requestKey.startsWith("/") && requestKey.includes(`${import_node_path3.default.sep}build${import_node_path3.default.sep}app${import_node_path3.default.sep}`);
|
|
1394
|
+
if (isStagingModuleId && isRuntimeBuildKey) {
|
|
1395
|
+
if (requestKey.startsWith("file://")) {
|
|
1396
|
+
try {
|
|
1397
|
+
return (0, import_node_url.fileURLToPath)(requestKey);
|
|
1398
|
+
} catch {
|
|
1399
|
+
return rawModuleId;
|
|
1400
|
+
}
|
|
1401
|
+
}
|
|
1402
|
+
return requestKey;
|
|
1403
|
+
}
|
|
1276
1404
|
return rawModuleId;
|
|
1277
1405
|
}
|
|
1278
1406
|
if (typeof rawModuleId !== "number" || !Number.isFinite(rawModuleId)) {
|
|
@@ -1354,6 +1482,14 @@ function createServerConsumerManifest(manifest) {
|
|
|
1354
1482
|
name: exportName
|
|
1355
1483
|
});
|
|
1356
1484
|
}
|
|
1485
|
+
} else if (typeof entry.id === "string" && entry.id.trim() !== "") {
|
|
1486
|
+
addReference(entry.id, "*", reference);
|
|
1487
|
+
for (const exportName of exportNames) {
|
|
1488
|
+
addReference(entry.id, exportName, {
|
|
1489
|
+
...reference,
|
|
1490
|
+
name: exportName
|
|
1491
|
+
});
|
|
1492
|
+
}
|
|
1357
1493
|
}
|
|
1358
1494
|
}
|
|
1359
1495
|
return consumerManifest;
|
|
@@ -1468,24 +1604,49 @@ function createNodeRequestHandler(options) {
|
|
|
1468
1604
|
if (url.pathname.startsWith(assetsPrefix)) {
|
|
1469
1605
|
const relative = url.pathname.slice(assetsPrefix.length);
|
|
1470
1606
|
const filePath = import_node_path3.default.resolve(distRootDir, relative);
|
|
1471
|
-
if (!filePath
|
|
1607
|
+
if (!isWithinDirectory(filePath, distRootDir)) {
|
|
1472
1608
|
res.statusCode = 400;
|
|
1473
1609
|
res.end("Invalid path");
|
|
1474
1610
|
return;
|
|
1475
1611
|
}
|
|
1476
1612
|
const ext = import_node_path3.default.extname(filePath);
|
|
1477
|
-
|
|
1478
|
-
|
|
1479
|
-
|
|
1480
|
-
|
|
1613
|
+
let stat;
|
|
1614
|
+
try {
|
|
1615
|
+
stat = import_node_fs2.default.statSync(filePath);
|
|
1616
|
+
if (!stat.isFile()) {
|
|
1617
|
+
throw new Error("Asset path is not a file");
|
|
1618
|
+
}
|
|
1619
|
+
} catch {
|
|
1620
|
+
res.statusCode = 404;
|
|
1621
|
+
res.end("Not found");
|
|
1622
|
+
return;
|
|
1481
1623
|
}
|
|
1482
|
-
res
|
|
1624
|
+
setAssetContentType(res, ext);
|
|
1625
|
+
const isDevelopmentAsset = nodeEnv !== "production";
|
|
1626
|
+
const isVersionedClientAsset = import_node_path3.default.basename(filePath) === "client.js" && url.searchParams.has("v");
|
|
1627
|
+
const canCacheLongTerm = !isDevelopmentAsset && (isHashedAssetPath(filePath) || isVersionedClientAsset);
|
|
1628
|
+
res.setHeader(
|
|
1629
|
+
"Cache-Control",
|
|
1630
|
+
canCacheLongTerm ? "public, max-age=31536000, immutable" : "no-store, no-cache, must-revalidate, proxy-revalidate"
|
|
1631
|
+
);
|
|
1632
|
+
res.setHeader("Vary", "Accept-Encoding");
|
|
1633
|
+
const contentEncoding = !isDevelopmentAsset ? getPreferredContentEncoding(req, ext, stat.size) : "";
|
|
1483
1634
|
const stream = import_node_fs2.default.createReadStream(filePath);
|
|
1484
1635
|
stream.on("error", () => {
|
|
1485
|
-
res.
|
|
1636
|
+
if (!res.headersSent) {
|
|
1637
|
+
res.statusCode = 404;
|
|
1638
|
+
}
|
|
1486
1639
|
res.end("Not found");
|
|
1487
1640
|
});
|
|
1488
|
-
|
|
1641
|
+
if (contentEncoding === "br") {
|
|
1642
|
+
res.setHeader("Content-Encoding", "br");
|
|
1643
|
+
stream.pipe((0, import_node_zlib.createBrotliCompress)()).pipe(res);
|
|
1644
|
+
} else if (contentEncoding === "gzip") {
|
|
1645
|
+
res.setHeader("Content-Encoding", "gzip");
|
|
1646
|
+
stream.pipe((0, import_node_zlib.createGzip)()).pipe(res);
|
|
1647
|
+
} else {
|
|
1648
|
+
stream.pipe(res);
|
|
1649
|
+
}
|
|
1489
1650
|
return;
|
|
1490
1651
|
}
|
|
1491
1652
|
const resolved = await withRequestBasename(
|
|
@@ -1503,22 +1664,23 @@ function createNodeRequestHandler(options) {
|
|
|
1503
1664
|
);
|
|
1504
1665
|
const initialPayload = {
|
|
1505
1666
|
model: resolved.model,
|
|
1506
|
-
contextModel: resolved.contextModel,
|
|
1507
|
-
pageModel: resolved.pageModel,
|
|
1508
1667
|
head: resolved.head
|
|
1509
1668
|
};
|
|
1510
1669
|
const initialFlightData = await renderRSCToString(initialPayload, {
|
|
1511
1670
|
moduleMap
|
|
1512
1671
|
});
|
|
1513
1672
|
const transportBasePath = normalizeRuntimeBasePath(resolved.head.transportBasePath) ?? normalizeRuntimeBasePath(basePath) ?? "";
|
|
1514
|
-
const shellClientScriptUrl =
|
|
1515
|
-
|
|
1516
|
-
|
|
1673
|
+
const shellClientScriptUrl = appendAssetVersion(
|
|
1674
|
+
joinRuntimeAssetPath(
|
|
1675
|
+
transportBasePath,
|
|
1676
|
+
clientScriptUrl
|
|
1677
|
+
),
|
|
1678
|
+
createClientAssetVersion(distRootDir)
|
|
1517
1679
|
);
|
|
1518
1680
|
const shellRscEndpoint = joinRuntimeBasePath(transportBasePath, "/rsc");
|
|
1519
1681
|
const shellBasename = normalizeRuntimeBasePath(resolved.head.basename) ?? normalizeRuntimeBasePath(basePath) ?? "";
|
|
1520
1682
|
const shellRouteBasePath = normalizeRuntimeBasePath(resolved.head.routeBasePath) ?? "";
|
|
1521
|
-
let rootHtml
|
|
1683
|
+
let rootHtml;
|
|
1522
1684
|
try {
|
|
1523
1685
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1524
1686
|
flightData: initialFlightData,
|
|
@@ -1542,29 +1704,23 @@ function createNodeRequestHandler(options) {
|
|
|
1542
1704
|
});
|
|
1543
1705
|
} catch (flightRenderError) {
|
|
1544
1706
|
console.error("[webframez-react] Flight-to-HTML render failed", flightRenderError);
|
|
1545
|
-
|
|
1546
|
-
|
|
1547
|
-
|
|
1548
|
-
|
|
1549
|
-
|
|
1550
|
-
|
|
1551
|
-
|
|
1552
|
-
|
|
1553
|
-
|
|
1554
|
-
initialFlightData,
|
|
1555
|
-
basename: shellBasename,
|
|
1556
|
-
routeBasePath: shellRouteBasePath,
|
|
1557
|
-
liveReloadPath: liveReloadPath || void 0,
|
|
1558
|
-
liveReloadServerId: liveReloadPath ? devServerId : void 0
|
|
1559
|
-
})
|
|
1707
|
+
sendTextResponse(
|
|
1708
|
+
req,
|
|
1709
|
+
res,
|
|
1710
|
+
createInitialHtmlErrorMarkup("Failed to render initial React HTML."),
|
|
1711
|
+
{
|
|
1712
|
+
statusCode: 500,
|
|
1713
|
+
contentType: "text/html; charset=utf-8",
|
|
1714
|
+
compress: nodeEnv === "production"
|
|
1715
|
+
}
|
|
1560
1716
|
);
|
|
1561
1717
|
return;
|
|
1562
1718
|
}
|
|
1563
1719
|
}
|
|
1564
1720
|
}
|
|
1565
|
-
|
|
1566
|
-
|
|
1567
|
-
|
|
1721
|
+
sendTextResponse(
|
|
1722
|
+
req,
|
|
1723
|
+
res,
|
|
1568
1724
|
createHTMLShell({
|
|
1569
1725
|
title: resolved.head.title || "Webframez React",
|
|
1570
1726
|
headTags: renderHeadToString(resolved.head),
|
|
@@ -1576,7 +1732,13 @@ function createNodeRequestHandler(options) {
|
|
|
1576
1732
|
routeBasePath: shellRouteBasePath,
|
|
1577
1733
|
liveReloadPath: liveReloadPath || void 0,
|
|
1578
1734
|
liveReloadServerId: liveReloadPath ? devServerId : void 0
|
|
1579
|
-
})
|
|
1735
|
+
}),
|
|
1736
|
+
{
|
|
1737
|
+
statusCode: resolved.statusCode,
|
|
1738
|
+
contentType: "text/html; charset=utf-8",
|
|
1739
|
+
cacheControl: "no-store, no-cache, must-revalidate, proxy-revalidate",
|
|
1740
|
+
compress: nodeEnv === "production"
|
|
1741
|
+
}
|
|
1580
1742
|
);
|
|
1581
1743
|
};
|
|
1582
1744
|
}
|