@webtypen/webframez-react 0.0.37 → 0.0.38
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/client.cjs +1 -1
- package/dist/client.js +1 -1
- package/dist/http.cjs +49 -13
- package/dist/http.js +49 -13
- package/dist/index.cjs +49 -13
- package/dist/index.js +49 -13
- package/dist/types.d.ts +1 -0
- package/dist/webframez-core.cjs +49 -13
- package/dist/webframez-core.js +49 -13
- package/package.json +1 -1
package/dist/client.cjs
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
var
|
|
1
|
+
var ce=Object.create;var E=Object.defineProperty;var de=Object.getOwnPropertyDescriptor;var ue=Object.getOwnPropertyNames;var le=Object.getPrototypeOf,fe=Object.prototype.hasOwnProperty;var pe=(e,t)=>{for(var n in t)E(e,n,{get:t[n],enumerable:!0})},U=(e,t,n,o)=>{if(t&&typeof t=="object"||typeof t=="function")for(let r of ue(t))!fe.call(e,r)&&r!==n&&E(e,r,{get:()=>t[r],enumerable:!(o=de(t,r))||o.enumerable});return e};var H=(e,t,n)=>(n=e!=null?ce(le(e)):{},U(t||!e||!e.__esModule?E(n,"default",{value:e,enumerable:!0}):n,e)),me=e=>U(E({},"__esModule",{value:!0}),e);var ke={};pe(ke,{mountWebframezClient:()=>Oe,useCookie:()=>Ne,useRouter:()=>ve});module.exports=me(ke);var s=H(require("react"),1),K=require("react-dom/client"),w=require("react-server-dom-webpack/client"),V=require("@webtypen/webframez-react/route-slot");var Re=/^(?:[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 z(e,t){let n=e.trim(),o=u(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 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=z(a.favicon,n)),a.links&&(a.links=a.links.map(c=>({...c,href:z(c.href,n)}))),a}var m=H(require("react"),1),D="webframez-route-children",W="__webframezRouteChildren",F="WebframezRouteChildren",N=()=>m.default.createElement(D);N.displayName=F;N[W]=!0;var we=N;function M(e){if(e===D||e===we)return!0;if(!e||typeof e!="function"&&typeof e!="object")return!1;try{let t=e;return t[W]===!0||t.displayName===F||t.name==="RouteChildren"}catch{return!1}}function $(e){if(!e||typeof e!="object")return!1;try{return"type"in e&&"props"in e}catch{return!1}}function A(e,t){if(e==null||typeof e=="boolean")return e;if(Array.isArray(e)){let l=!1,_=e.map(p=>{let h=A(p,t);return h!==p&&(l=!0),h});return l?_:e}if($(e)&&M(e.type))return t;let n=m.default.isValidElement(e);if(!n&&!$(e))return e;if(n&&M(e.type))return t;let o=e.props??{};if(!("children"in o))return e;let r=A(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"),_e={push:()=>{},replace:()=>{},refresh:()=>{},refreshContext:()=>{}},T=typeof s.default.createContext=="function"?s.default.createContext(null):null,X="__WEBFRAMEZ_ROUTER__",he="__WEBFRAMEZ_REACT_BUILD_ID",ge="x-webframez-react-build",Ce="[data-webframez-head='true']";function j(){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 I(e){return u(e)??""}function ye(e,t){return t?e===t?"/":e.startsWith(`${t}/`)?e.slice(t.length)||"/":e||"/":e||"/"}function J(e,t){let n=!t||t==="/"?"/":t.startsWith("/")?t:`/${t}`;return e?n==="/"?e:`${e}${n}`:n}function Ee(){return I(typeof window>"u"?globalThis.__RSC_ROUTE_BASE_PATH:window.__RSC_ROUTE_BASE_PATH)}function Q(e){if(typeof window>"u")return e||"/";let t=I(window.__RSC_BASENAME),n=Ee(),o=ye(e||"/",t);return J(n,o)}function ee(e){if(typeof window>"u")return e;let t=window.__RSC_ENDPOINT;return typeof t=="string"&&t.trim()!==""?t:e}function Ae(){if(typeof window>"u")return"";let e=window[he];return typeof e=="string"?e:""}function Te(e){let t=Ae();return!!t&&!!e&&t!==e}function v(e){typeof window>"u"||window.location.assign(`${e.pathname}${e.search}${e.hash}`)}function Pe(){return typeof window>"u"?null:window[X]??null}function Se(e){typeof window>"u"||(window[X]=e)}function G(){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 Ne(){return s.default.useMemo(()=>({all:()=>G(),get:e=>G()[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 ve(){let e=T?s.default.useContext(T):null;if(!e){let t=Pe();if(t)return t;if(typeof window>"u")return _e;throw new Error("useRouter must be used inside mountWebframezClient()")}return e}function xe({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 Y(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 Z(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;te(t),document.title=t.title||"Webframez React";for(let n of document.head.querySelectorAll(Ce))n.remove();t.description&&Y({name:"description",content:t.description}),t.favicon&&Z({rel:"icon",href:t.favicon});for(let n of t.meta??[])Y(n);for(let n of t.links??[])Z(n)}function te(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=J(r,"/rsc"))}function Ie(e){let t=new TextEncoder;return new ReadableStream({start(n){n.enqueue(t.encode(e)),n.close()}})}function Be(){if(typeof window>"u")return null;let e=window.__RSC_INITIAL_PAYLOAD;return typeof e!="string"||e===""?null:(delete window.__RSC_INITIAL_PAYLOAD,(0,w.createFromReadableStream)(Ie(e)))}function Le(e){let t=ee(e),n=Q(window.location.pathname);return Be()??(0,w.createFromFetch)(fetch(`${t}?path=${encodeURIComponent(n)}&search=${encodeURIComponent(window.location.search)}`,{cache:"no-store",credentials:"same-origin",headers:{Accept:"text/x-component"}}))}function be(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,_]=(0,s.useState)(o.contextModel),[p,h]=(0,s.useState)(o.pageModel),[B,L]=(0,s.useState)(o.head),[ne,g]=(0,s.useState)(!1),[oe,re]=(0,s.useState)(!1),[ie,P]=(0,s.useState)(r);async function b(i){let y=ee(t),f=Q(i.pathname),R=await fetch(`${y}?path=${encodeURIComponent(f)}&search=${encodeURIComponent(i.search)}`,{cache:"no-store",credentials:"same-origin",headers:{Accept:"text/x-component"}});return Te(R.headers.get(ge))?(v(i),await new Promise(()=>{})):await(0,w.createFromFetch)(Promise.resolve(R))}async function C(i,y="push"){g(!0);try{let f=await b(i);x(f.head),L(f.head),c(f.model),_(f.contextModel),h(f.pageModel),P(!0);let R=`${i.pathname}${i.search}${i.hash}`;y==="replace"?(history.replaceState(null,"",R),j()):y==="push"&&(history.pushState(null,"",R),j())}catch(f){console.error("[webframez-react] Failed to render route",f),v(i),c((0,d.jsx)("p",{children:"Failed to load route."}))}finally{g(!1)}}async function ae(){g(!0);try{let i=await b(new URL(window.location.href));if(x(i.head),L(i.head),Object.prototype.hasOwnProperty.call(i,"contextModel")){_(i.contextModel),P(!0);return}c(i.model),P(!1)}catch(i){console.error("[webframez-react] Failed to refresh route context",i),v(new URL(window.location.href))}finally{g(!1)}}(0,s.useEffect)(()=>{x(B)},[B]),(0,s.useEffect)(()=>{re(!0);let i=()=>{C(new URL(window.location.href),"none")};return window.addEventListener("popstate",i),()=>{window.removeEventListener("popstate",i)}},[]);let O=s.default.useMemo(()=>({push:i=>{C(new URL(i,window.location.origin),"push")},replace:i=>{C(new URL(i,window.location.origin),"replace")},refresh:()=>{C(new URL(window.location.href),"none")},refreshContext:()=>{ae()}}),[]);Se(O);let se=ie&&typeof p<"u"?l?(0,d.jsx)(V.RouteChildrenSlotProvider,{page:p,children:A(l,p)}):p:a,k=(0,d.jsxs)(d.Fragment,{children:[oe?(0,d.jsx)(xe,{active:ne}):null,se??(0,d.jsx)("p",{style:{padding:24},children:"Loading..."})]});return T?(0,d.jsx)(T.Provider,{value:O,children:k}):k}}function Oe(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(Le(r)).then(l=>(l?.head&&te(l.head),l)),c=be(a,r);return(0,K.hydrateRoot)(n,(0,d.jsx)(c,{}))}
|
package/dist/client.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import m,{useEffect as
|
|
1
|
+
import m,{useEffect as D,useState as f}from"react";import{hydrateRoot as se}from"react-dom/client";import{createFromFetch as Y,createFromReadableStream as ce}from"react-server-dom-webpack/client";import{RouteChildrenSlotProvider as de}from"@webtypen/webframez-react/route-slot";var ie=/^(?:[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 k(e,t){let n=e.trim(),o=c(t);return!n||!o||ie.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=k(a.favicon,n)),a.links&&(a.links=a.links.map(s=>({...s,href:k(s.href,n)}))),a}import w from"react";var z="webframez-route-children",M="__webframezRouteChildren",$="WebframezRouteChildren",S=()=>w.createElement(z);S.displayName=$;S[M]=!0;var ae=S;function U(e){if(e===z||e===ae)return!0;if(!e||typeof e!="function"&&typeof e!="object")return!1;try{let t=e;return t[M]===!0||t.displayName===$||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 E(e,t){if(e==null||typeof e=="boolean")return e;if(Array.isArray(e)){let d=!1,_=e.map(l=>{let h=E(l,t);return h!==l&&(d=!0),h});return d?_:e}if(H(e)&&U(e.type))return t;let n=w.isValidElement(e);if(!n&&!H(e))return e;if(n&&U(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)?w.cloneElement(e,void 0,...r):w.cloneElement(e,void 0,r);let a=e,s={...a.props??{},children:r,...a.key!==void 0&&a.key!==null?{key:a.key}:{}};return w.createElement(a.type,s)}import{Fragment as Pe,jsx as p,jsxs as Se}from"react/jsx-runtime";var ue={push:()=>{},replace:()=>{},refresh:()=>{},refreshContext:()=>{}},A=typeof m.createContext=="function"?m.createContext(null):null,Z="__WEBFRAMEZ_ROUTER__",le="__WEBFRAMEZ_REACT_BUILD_ID",fe="x-webframez-react-build",pe="[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 me(e,t){return t?e===t?"/":e.startsWith(`${t}/`)?e.slice(t.length)||"/":e||"/":e||"/"}function K(e,t){let n=!t||t==="/"?"/":t.startsWith("/")?t:`/${t}`;return e?n==="/"?e:`${e}${n}`:n}function Re(){return x(typeof window>"u"?globalThis.__RSC_ROUTE_BASE_PATH:window.__RSC_ROUTE_BASE_PATH)}function V(e){if(typeof window>"u")return e||"/";let t=x(window.__RSC_BASENAME),n=Re(),o=me(e||"/",t);return K(n,o)}function X(e){if(typeof window>"u")return e;let t=window.__RSC_ENDPOINT;return typeof t=="string"&&t.trim()!==""?t:e}function we(){if(typeof window>"u")return"";let e=window[le];return typeof e=="string"?e:""}function _e(e){let t=we();return!!t&&!!e&&t!==e}function N(e){typeof window>"u"||window.location.assign(`${e.pathname}${e.search}${e.hash}`)}function he(){return typeof window>"u"?null:window[Z]??null}function ge(e){typeof window>"u"||(window[Z]=e)}function F(){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 j(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 He(){return m.useMemo(()=>({all:()=>F(),get:e=>F()[e],set:(e,t,n)=>{typeof document>"u"||(document.cookie=j(e,t,n))},remove:(e,t)=>{typeof document>"u"||(document.cookie=j(e,"",{...t??{},maxAge:0}))}}),[])}function ze(){let e=A?m.useContext(A):null;if(!e){let t=he();if(t)return t;if(typeof window>"u")return ue;throw new Error("useRouter must be used inside mountWebframezClient()")}return e}function Ce({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 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 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 v(e){if(typeof document>"u")return;let t=P(e)??e;J(t),document.title=t.title||"Webframez React";for(let n of document.head.querySelectorAll(pe))n.remove();t.description&&G({name:"description",content:t.description}),t.favicon&&q({rel:"icon",href:t.favicon});for(let n of t.meta??[])G(n);for(let n of t.links??[])q(n)}function J(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=K(r,"/rsc"))}function ye(e){let t=new TextEncoder;return new ReadableStream({start(n){n.enqueue(t.encode(e)),n.close()}})}function Ee(){if(typeof window>"u")return null;let e=window.__RSC_INITIAL_PAYLOAD;return typeof e!="string"||e===""?null:(delete window.__RSC_INITIAL_PAYLOAD,ce(ye(e)))}function Ae(e){let t=X(e),n=V(window.location.pathname);return Ee()??Y(fetch(`${t}?path=${encodeURIComponent(n)}&search=${encodeURIComponent(window.location.search)}`,{cache:"no-store",credentials:"same-origin",headers:{Accept:"text/x-component"}}))}function Te(e,t){return function(){let o=m.use(e),r=typeof o.contextModel<"u"&&typeof o.pageModel<"u",[a,s]=f(o.model),[d,_]=f(o.contextModel),[l,h]=f(o.pageModel),[I,B]=f(o.head),[Q,g]=f(!1),[ee,te]=f(!1),[ne,T]=f(r);async function L(i){let y=X(t),u=V(i.pathname),R=await fetch(`${y}?path=${encodeURIComponent(u)}&search=${encodeURIComponent(i.search)}`,{cache:"no-store",credentials:"same-origin",headers:{Accept:"text/x-component"}});return _e(R.headers.get(fe))?(N(i),await new Promise(()=>{})):await Y(Promise.resolve(R))}async function C(i,y="push"){g(!0);try{let u=await L(i);v(u.head),B(u.head),s(u.model),_(u.contextModel),h(u.pageModel),T(!0);let R=`${i.pathname}${i.search}${i.hash}`;y==="replace"?(history.replaceState(null,"",R),W()):y==="push"&&(history.pushState(null,"",R),W())}catch(u){console.error("[webframez-react] Failed to render route",u),N(i),s(p("p",{children:"Failed to load route."}))}finally{g(!1)}}async function oe(){g(!0);try{let i=await L(new URL(window.location.href));if(v(i.head),B(i.head),Object.prototype.hasOwnProperty.call(i,"contextModel")){_(i.contextModel),T(!0);return}s(i.model),T(!1)}catch(i){console.error("[webframez-react] Failed to refresh route context",i),N(new URL(window.location.href))}finally{g(!1)}}D(()=>{v(I)},[I]),D(()=>{te(!0);let i=()=>{C(new URL(window.location.href),"none")};return window.addEventListener("popstate",i),()=>{window.removeEventListener("popstate",i)}},[]);let b=m.useMemo(()=>({push:i=>{C(new URL(i,window.location.origin),"push")},replace:i=>{C(new URL(i,window.location.origin),"replace")},refresh:()=>{C(new URL(window.location.href),"none")},refreshContext:()=>{oe()}}),[]);ge(b);let re=ne&&typeof l<"u"?d?p(de,{page:l,children:E(d,l)}):l:a,O=Se(Pe,{children:[ee?p(Ce,{active:Q}):null,re??p("p",{style:{padding:24},children:"Loading..."})]});return A?p(A.Provider,{value:b,children:O}):O}}function Me(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(Ae(r)).then(d=>(d?.head&&J(d.head),d)),s=Te(a,r);return se(n,p(s,{}))}export{Me as mountWebframezClient,He as useCookie,ze as useRouter};
|
package/dist/http.cjs
CHANGED
|
@@ -52,6 +52,7 @@ function createHTMLShell(options = {}) {
|
|
|
52
52
|
title = "RSC App",
|
|
53
53
|
rscEndpoint = "/rsc",
|
|
54
54
|
clientScriptUrl = "/client.js",
|
|
55
|
+
buildId = "",
|
|
55
56
|
headTags = "",
|
|
56
57
|
rootHtml = "",
|
|
57
58
|
initialFlightData = "",
|
|
@@ -106,6 +107,7 @@ function createHTMLShell(options = {}) {
|
|
|
106
107
|
<script>window.__RSC_ENDPOINT = "${rscEndpoint}";</script>
|
|
107
108
|
<script>window.__RSC_BASENAME = "${basename}";</script>
|
|
108
109
|
<script>window.__RSC_ROUTE_BASE_PATH = "${routeBasePath}";</script>
|
|
110
|
+
<script>window.__WEBFRAMEZ_REACT_BUILD_ID = "${buildId}";</script>
|
|
109
111
|
<script>window.__RSC_INITIAL_PAYLOAD = ${escapedInitialFlightData};</script>
|
|
110
112
|
<script type="module" src="${clientScriptUrl}"></script>
|
|
111
113
|
${liveReloadScript}
|
|
@@ -801,6 +803,15 @@ function createClientAssetVersion(distRootDir) {
|
|
|
801
803
|
return "";
|
|
802
804
|
}
|
|
803
805
|
}
|
|
806
|
+
function createBuildId(distRootDir, manifestPath) {
|
|
807
|
+
const clientVersion = createClientAssetVersion(distRootDir);
|
|
808
|
+
try {
|
|
809
|
+
const stat = import_node_fs2.default.statSync(manifestPath);
|
|
810
|
+
return `${clientVersion}:${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
811
|
+
} catch {
|
|
812
|
+
return clientVersion;
|
|
813
|
+
}
|
|
814
|
+
}
|
|
804
815
|
function appendAssetVersion(url, version) {
|
|
805
816
|
if (!version) {
|
|
806
817
|
return url;
|
|
@@ -1494,6 +1505,30 @@ function createServerConsumerManifest(manifest) {
|
|
|
1494
1505
|
}
|
|
1495
1506
|
return consumerManifest;
|
|
1496
1507
|
}
|
|
1508
|
+
function createManifestLoader(options) {
|
|
1509
|
+
let cache = null;
|
|
1510
|
+
return () => {
|
|
1511
|
+
const stat = import_node_fs2.default.statSync(options.manifestPath);
|
|
1512
|
+
const cacheKey = `${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
1513
|
+
if (cache && cache.cacheKey === cacheKey) {
|
|
1514
|
+
return cache;
|
|
1515
|
+
}
|
|
1516
|
+
const moduleMap = normalizeClientManifest(
|
|
1517
|
+
JSON.parse(import_node_fs2.default.readFileSync(options.manifestPath, "utf-8")),
|
|
1518
|
+
{
|
|
1519
|
+
distRootDir: options.distRootDir,
|
|
1520
|
+
cwd: options.cwd
|
|
1521
|
+
}
|
|
1522
|
+
);
|
|
1523
|
+
cache = {
|
|
1524
|
+
cacheKey,
|
|
1525
|
+
buildId: createBuildId(options.distRootDir, options.manifestPath),
|
|
1526
|
+
moduleMap,
|
|
1527
|
+
serverConsumerModuleMap: createServerConsumerManifest(moduleMap)
|
|
1528
|
+
};
|
|
1529
|
+
return cache;
|
|
1530
|
+
};
|
|
1531
|
+
}
|
|
1497
1532
|
function createNodeRequestHandler(options) {
|
|
1498
1533
|
const devServerId = `${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 8)}`;
|
|
1499
1534
|
const distRootDir = import_node_path3.default.resolve(options.distRootDir);
|
|
@@ -1511,14 +1546,11 @@ function createNodeRequestHandler(options) {
|
|
|
1511
1546
|
const liveReloadPath = !liveReloadEnabled ? "" : options.liveReloadPath ?? `${basePath || ""}/__webframez_live_reload`;
|
|
1512
1547
|
const liveReloadClients = /* @__PURE__ */ new Set();
|
|
1513
1548
|
const router = createFileRouter({ pagesDir });
|
|
1514
|
-
const
|
|
1515
|
-
|
|
1516
|
-
|
|
1517
|
-
|
|
1518
|
-
|
|
1519
|
-
}
|
|
1520
|
-
);
|
|
1521
|
-
const serverConsumerModuleMap = createServerConsumerManifest(moduleMap);
|
|
1549
|
+
const getManifestState = createManifestLoader({
|
|
1550
|
+
distRootDir,
|
|
1551
|
+
manifestPath,
|
|
1552
|
+
cwd: process.cwd()
|
|
1553
|
+
});
|
|
1522
1554
|
const initialHtmlWorker = createInitialHtmlWorker(pagesDir);
|
|
1523
1555
|
const disposeInitialHtmlWorker = () => {
|
|
1524
1556
|
initialHtmlWorker.dispose();
|
|
@@ -1573,6 +1605,7 @@ function createNodeRequestHandler(options) {
|
|
|
1573
1605
|
return;
|
|
1574
1606
|
}
|
|
1575
1607
|
if (url.pathname === rscPath) {
|
|
1608
|
+
const manifestState2 = getManifestState();
|
|
1576
1609
|
const pathname = stripBasePath(url.searchParams.get("path") || "/", basePath);
|
|
1577
1610
|
const requestContext = createRouteRequestContext(
|
|
1578
1611
|
req,
|
|
@@ -1595,8 +1628,9 @@ function createNodeRequestHandler(options) {
|
|
|
1595
1628
|
pageModel: resolved2.pageModel,
|
|
1596
1629
|
head: resolved2.head
|
|
1597
1630
|
};
|
|
1631
|
+
res.setHeader("X-Webframez-React-Build", manifestState2.buildId);
|
|
1598
1632
|
sendRSC(res, payload, {
|
|
1599
|
-
moduleMap,
|
|
1633
|
+
moduleMap: manifestState2.moduleMap,
|
|
1600
1634
|
statusCode: resolved2.statusCode
|
|
1601
1635
|
});
|
|
1602
1636
|
return;
|
|
@@ -1666,8 +1700,9 @@ function createNodeRequestHandler(options) {
|
|
|
1666
1700
|
model: resolved.model,
|
|
1667
1701
|
head: resolved.head
|
|
1668
1702
|
};
|
|
1703
|
+
const manifestState = getManifestState();
|
|
1669
1704
|
const initialFlightData = await renderRSCToString(initialPayload, {
|
|
1670
|
-
moduleMap
|
|
1705
|
+
moduleMap: manifestState.moduleMap
|
|
1671
1706
|
});
|
|
1672
1707
|
const transportBasePath = normalizeRuntimeBasePath(resolved.head.transportBasePath) ?? normalizeRuntimeBasePath(basePath) ?? "";
|
|
1673
1708
|
const shellClientScriptUrl = appendAssetVersion(
|
|
@@ -1684,7 +1719,7 @@ function createNodeRequestHandler(options) {
|
|
|
1684
1719
|
try {
|
|
1685
1720
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1686
1721
|
flightData: initialFlightData,
|
|
1687
|
-
moduleMap: serverConsumerModuleMap
|
|
1722
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1688
1723
|
});
|
|
1689
1724
|
} catch (error) {
|
|
1690
1725
|
console.error("[webframez-react] Failed to render initial HTML", error);
|
|
@@ -1692,7 +1727,7 @@ function createNodeRequestHandler(options) {
|
|
|
1692
1727
|
initialHtmlWorker.dispose();
|
|
1693
1728
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1694
1729
|
flightData: initialFlightData,
|
|
1695
|
-
moduleMap: serverConsumerModuleMap
|
|
1730
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1696
1731
|
});
|
|
1697
1732
|
} catch (retryError) {
|
|
1698
1733
|
console.error("[webframez-react] Retry for initial HTML failed", retryError);
|
|
@@ -1700,7 +1735,7 @@ function createNodeRequestHandler(options) {
|
|
|
1700
1735
|
initialHtmlWorker.dispose();
|
|
1701
1736
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1702
1737
|
flightData: initialFlightData,
|
|
1703
|
-
moduleMap: serverConsumerModuleMap
|
|
1738
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1704
1739
|
});
|
|
1705
1740
|
} catch (flightRenderError) {
|
|
1706
1741
|
console.error("[webframez-react] Flight-to-HTML render failed", flightRenderError);
|
|
@@ -1725,6 +1760,7 @@ function createNodeRequestHandler(options) {
|
|
|
1725
1760
|
title: resolved.head.title || "Webframez React",
|
|
1726
1761
|
headTags: renderHeadToString(resolved.head),
|
|
1727
1762
|
clientScriptUrl: shellClientScriptUrl,
|
|
1763
|
+
buildId: manifestState.buildId,
|
|
1728
1764
|
rscEndpoint: shellRscEndpoint,
|
|
1729
1765
|
rootHtml,
|
|
1730
1766
|
initialFlightData,
|
package/dist/http.js
CHANGED
|
@@ -32,6 +32,7 @@ function createHTMLShell(options = {}) {
|
|
|
32
32
|
title = "RSC App",
|
|
33
33
|
rscEndpoint = "/rsc",
|
|
34
34
|
clientScriptUrl = "/client.js",
|
|
35
|
+
buildId = "",
|
|
35
36
|
headTags = "",
|
|
36
37
|
rootHtml = "",
|
|
37
38
|
initialFlightData = "",
|
|
@@ -86,6 +87,7 @@ function createHTMLShell(options = {}) {
|
|
|
86
87
|
<script>window.__RSC_ENDPOINT = "${rscEndpoint}";</script>
|
|
87
88
|
<script>window.__RSC_BASENAME = "${basename}";</script>
|
|
88
89
|
<script>window.__RSC_ROUTE_BASE_PATH = "${routeBasePath}";</script>
|
|
90
|
+
<script>window.__WEBFRAMEZ_REACT_BUILD_ID = "${buildId}";</script>
|
|
89
91
|
<script>window.__RSC_INITIAL_PAYLOAD = ${escapedInitialFlightData};</script>
|
|
90
92
|
<script type="module" src="${clientScriptUrl}"></script>
|
|
91
93
|
${liveReloadScript}
|
|
@@ -781,6 +783,15 @@ function createClientAssetVersion(distRootDir) {
|
|
|
781
783
|
return "";
|
|
782
784
|
}
|
|
783
785
|
}
|
|
786
|
+
function createBuildId(distRootDir, manifestPath) {
|
|
787
|
+
const clientVersion = createClientAssetVersion(distRootDir);
|
|
788
|
+
try {
|
|
789
|
+
const stat = fs2.statSync(manifestPath);
|
|
790
|
+
return `${clientVersion}:${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
791
|
+
} catch {
|
|
792
|
+
return clientVersion;
|
|
793
|
+
}
|
|
794
|
+
}
|
|
784
795
|
function appendAssetVersion(url, version) {
|
|
785
796
|
if (!version) {
|
|
786
797
|
return url;
|
|
@@ -1474,6 +1485,30 @@ function createServerConsumerManifest(manifest) {
|
|
|
1474
1485
|
}
|
|
1475
1486
|
return consumerManifest;
|
|
1476
1487
|
}
|
|
1488
|
+
function createManifestLoader(options) {
|
|
1489
|
+
let cache = null;
|
|
1490
|
+
return () => {
|
|
1491
|
+
const stat = fs2.statSync(options.manifestPath);
|
|
1492
|
+
const cacheKey = `${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
1493
|
+
if (cache && cache.cacheKey === cacheKey) {
|
|
1494
|
+
return cache;
|
|
1495
|
+
}
|
|
1496
|
+
const moduleMap = normalizeClientManifest(
|
|
1497
|
+
JSON.parse(fs2.readFileSync(options.manifestPath, "utf-8")),
|
|
1498
|
+
{
|
|
1499
|
+
distRootDir: options.distRootDir,
|
|
1500
|
+
cwd: options.cwd
|
|
1501
|
+
}
|
|
1502
|
+
);
|
|
1503
|
+
cache = {
|
|
1504
|
+
cacheKey,
|
|
1505
|
+
buildId: createBuildId(options.distRootDir, options.manifestPath),
|
|
1506
|
+
moduleMap,
|
|
1507
|
+
serverConsumerModuleMap: createServerConsumerManifest(moduleMap)
|
|
1508
|
+
};
|
|
1509
|
+
return cache;
|
|
1510
|
+
};
|
|
1511
|
+
}
|
|
1477
1512
|
function createNodeRequestHandler(options) {
|
|
1478
1513
|
const devServerId = `${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 8)}`;
|
|
1479
1514
|
const distRootDir = path3.resolve(options.distRootDir);
|
|
@@ -1491,14 +1526,11 @@ function createNodeRequestHandler(options) {
|
|
|
1491
1526
|
const liveReloadPath = !liveReloadEnabled ? "" : options.liveReloadPath ?? `${basePath || ""}/__webframez_live_reload`;
|
|
1492
1527
|
const liveReloadClients = /* @__PURE__ */ new Set();
|
|
1493
1528
|
const router = createFileRouter({ pagesDir });
|
|
1494
|
-
const
|
|
1495
|
-
|
|
1496
|
-
|
|
1497
|
-
|
|
1498
|
-
|
|
1499
|
-
}
|
|
1500
|
-
);
|
|
1501
|
-
const serverConsumerModuleMap = createServerConsumerManifest(moduleMap);
|
|
1529
|
+
const getManifestState = createManifestLoader({
|
|
1530
|
+
distRootDir,
|
|
1531
|
+
manifestPath,
|
|
1532
|
+
cwd: process.cwd()
|
|
1533
|
+
});
|
|
1502
1534
|
const initialHtmlWorker = createInitialHtmlWorker(pagesDir);
|
|
1503
1535
|
const disposeInitialHtmlWorker = () => {
|
|
1504
1536
|
initialHtmlWorker.dispose();
|
|
@@ -1553,6 +1585,7 @@ function createNodeRequestHandler(options) {
|
|
|
1553
1585
|
return;
|
|
1554
1586
|
}
|
|
1555
1587
|
if (url.pathname === rscPath) {
|
|
1588
|
+
const manifestState2 = getManifestState();
|
|
1556
1589
|
const pathname = stripBasePath(url.searchParams.get("path") || "/", basePath);
|
|
1557
1590
|
const requestContext = createRouteRequestContext(
|
|
1558
1591
|
req,
|
|
@@ -1575,8 +1608,9 @@ function createNodeRequestHandler(options) {
|
|
|
1575
1608
|
pageModel: resolved2.pageModel,
|
|
1576
1609
|
head: resolved2.head
|
|
1577
1610
|
};
|
|
1611
|
+
res.setHeader("X-Webframez-React-Build", manifestState2.buildId);
|
|
1578
1612
|
sendRSC(res, payload, {
|
|
1579
|
-
moduleMap,
|
|
1613
|
+
moduleMap: manifestState2.moduleMap,
|
|
1580
1614
|
statusCode: resolved2.statusCode
|
|
1581
1615
|
});
|
|
1582
1616
|
return;
|
|
@@ -1646,8 +1680,9 @@ function createNodeRequestHandler(options) {
|
|
|
1646
1680
|
model: resolved.model,
|
|
1647
1681
|
head: resolved.head
|
|
1648
1682
|
};
|
|
1683
|
+
const manifestState = getManifestState();
|
|
1649
1684
|
const initialFlightData = await renderRSCToString(initialPayload, {
|
|
1650
|
-
moduleMap
|
|
1685
|
+
moduleMap: manifestState.moduleMap
|
|
1651
1686
|
});
|
|
1652
1687
|
const transportBasePath = normalizeRuntimeBasePath(resolved.head.transportBasePath) ?? normalizeRuntimeBasePath(basePath) ?? "";
|
|
1653
1688
|
const shellClientScriptUrl = appendAssetVersion(
|
|
@@ -1664,7 +1699,7 @@ function createNodeRequestHandler(options) {
|
|
|
1664
1699
|
try {
|
|
1665
1700
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1666
1701
|
flightData: initialFlightData,
|
|
1667
|
-
moduleMap: serverConsumerModuleMap
|
|
1702
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1668
1703
|
});
|
|
1669
1704
|
} catch (error) {
|
|
1670
1705
|
console.error("[webframez-react] Failed to render initial HTML", error);
|
|
@@ -1672,7 +1707,7 @@ function createNodeRequestHandler(options) {
|
|
|
1672
1707
|
initialHtmlWorker.dispose();
|
|
1673
1708
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1674
1709
|
flightData: initialFlightData,
|
|
1675
|
-
moduleMap: serverConsumerModuleMap
|
|
1710
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1676
1711
|
});
|
|
1677
1712
|
} catch (retryError) {
|
|
1678
1713
|
console.error("[webframez-react] Retry for initial HTML failed", retryError);
|
|
@@ -1680,7 +1715,7 @@ function createNodeRequestHandler(options) {
|
|
|
1680
1715
|
initialHtmlWorker.dispose();
|
|
1681
1716
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1682
1717
|
flightData: initialFlightData,
|
|
1683
|
-
moduleMap: serverConsumerModuleMap
|
|
1718
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1684
1719
|
});
|
|
1685
1720
|
} catch (flightRenderError) {
|
|
1686
1721
|
console.error("[webframez-react] Flight-to-HTML render failed", flightRenderError);
|
|
@@ -1705,6 +1740,7 @@ function createNodeRequestHandler(options) {
|
|
|
1705
1740
|
title: resolved.head.title || "Webframez React",
|
|
1706
1741
|
headTags: renderHeadToString(resolved.head),
|
|
1707
1742
|
clientScriptUrl: shellClientScriptUrl,
|
|
1743
|
+
buildId: manifestState.buildId,
|
|
1708
1744
|
rscEndpoint: shellRscEndpoint,
|
|
1709
1745
|
rootHtml,
|
|
1710
1746
|
initialFlightData,
|
package/dist/index.cjs
CHANGED
|
@@ -59,6 +59,7 @@ function createHTMLShell(options = {}) {
|
|
|
59
59
|
title = "RSC App",
|
|
60
60
|
rscEndpoint = "/rsc",
|
|
61
61
|
clientScriptUrl = "/client.js",
|
|
62
|
+
buildId = "",
|
|
62
63
|
headTags = "",
|
|
63
64
|
rootHtml = "",
|
|
64
65
|
initialFlightData = "",
|
|
@@ -113,6 +114,7 @@ function createHTMLShell(options = {}) {
|
|
|
113
114
|
<script>window.__RSC_ENDPOINT = "${rscEndpoint}";</script>
|
|
114
115
|
<script>window.__RSC_BASENAME = "${basename}";</script>
|
|
115
116
|
<script>window.__RSC_ROUTE_BASE_PATH = "${routeBasePath}";</script>
|
|
117
|
+
<script>window.__WEBFRAMEZ_REACT_BUILD_ID = "${buildId}";</script>
|
|
116
118
|
<script>window.__RSC_INITIAL_PAYLOAD = ${escapedInitialFlightData};</script>
|
|
117
119
|
<script type="module" src="${clientScriptUrl}"></script>
|
|
118
120
|
${liveReloadScript}
|
|
@@ -841,6 +843,15 @@ function createClientAssetVersion(distRootDir) {
|
|
|
841
843
|
return "";
|
|
842
844
|
}
|
|
843
845
|
}
|
|
846
|
+
function createBuildId(distRootDir, manifestPath) {
|
|
847
|
+
const clientVersion = createClientAssetVersion(distRootDir);
|
|
848
|
+
try {
|
|
849
|
+
const stat = import_node_fs2.default.statSync(manifestPath);
|
|
850
|
+
return `${clientVersion}:${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
851
|
+
} catch {
|
|
852
|
+
return clientVersion;
|
|
853
|
+
}
|
|
854
|
+
}
|
|
844
855
|
function appendAssetVersion(url, version) {
|
|
845
856
|
if (!version) {
|
|
846
857
|
return url;
|
|
@@ -1534,6 +1545,30 @@ function createServerConsumerManifest(manifest) {
|
|
|
1534
1545
|
}
|
|
1535
1546
|
return consumerManifest;
|
|
1536
1547
|
}
|
|
1548
|
+
function createManifestLoader(options) {
|
|
1549
|
+
let cache = null;
|
|
1550
|
+
return () => {
|
|
1551
|
+
const stat = import_node_fs2.default.statSync(options.manifestPath);
|
|
1552
|
+
const cacheKey = `${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
1553
|
+
if (cache && cache.cacheKey === cacheKey) {
|
|
1554
|
+
return cache;
|
|
1555
|
+
}
|
|
1556
|
+
const moduleMap = normalizeClientManifest(
|
|
1557
|
+
JSON.parse(import_node_fs2.default.readFileSync(options.manifestPath, "utf-8")),
|
|
1558
|
+
{
|
|
1559
|
+
distRootDir: options.distRootDir,
|
|
1560
|
+
cwd: options.cwd
|
|
1561
|
+
}
|
|
1562
|
+
);
|
|
1563
|
+
cache = {
|
|
1564
|
+
cacheKey,
|
|
1565
|
+
buildId: createBuildId(options.distRootDir, options.manifestPath),
|
|
1566
|
+
moduleMap,
|
|
1567
|
+
serverConsumerModuleMap: createServerConsumerManifest(moduleMap)
|
|
1568
|
+
};
|
|
1569
|
+
return cache;
|
|
1570
|
+
};
|
|
1571
|
+
}
|
|
1537
1572
|
function createNodeRequestHandler(options) {
|
|
1538
1573
|
const devServerId = `${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 8)}`;
|
|
1539
1574
|
const distRootDir = import_node_path3.default.resolve(options.distRootDir);
|
|
@@ -1551,14 +1586,11 @@ function createNodeRequestHandler(options) {
|
|
|
1551
1586
|
const liveReloadPath = !liveReloadEnabled ? "" : options.liveReloadPath ?? `${basePath || ""}/__webframez_live_reload`;
|
|
1552
1587
|
const liveReloadClients = /* @__PURE__ */ new Set();
|
|
1553
1588
|
const router = createFileRouter({ pagesDir });
|
|
1554
|
-
const
|
|
1555
|
-
|
|
1556
|
-
|
|
1557
|
-
|
|
1558
|
-
|
|
1559
|
-
}
|
|
1560
|
-
);
|
|
1561
|
-
const serverConsumerModuleMap = createServerConsumerManifest(moduleMap);
|
|
1589
|
+
const getManifestState = createManifestLoader({
|
|
1590
|
+
distRootDir,
|
|
1591
|
+
manifestPath,
|
|
1592
|
+
cwd: process.cwd()
|
|
1593
|
+
});
|
|
1562
1594
|
const initialHtmlWorker = createInitialHtmlWorker(pagesDir);
|
|
1563
1595
|
const disposeInitialHtmlWorker = () => {
|
|
1564
1596
|
initialHtmlWorker.dispose();
|
|
@@ -1613,6 +1645,7 @@ function createNodeRequestHandler(options) {
|
|
|
1613
1645
|
return;
|
|
1614
1646
|
}
|
|
1615
1647
|
if (url.pathname === rscPath) {
|
|
1648
|
+
const manifestState2 = getManifestState();
|
|
1616
1649
|
const pathname = stripBasePath(url.searchParams.get("path") || "/", basePath);
|
|
1617
1650
|
const requestContext = createRouteRequestContext(
|
|
1618
1651
|
req,
|
|
@@ -1635,8 +1668,9 @@ function createNodeRequestHandler(options) {
|
|
|
1635
1668
|
pageModel: resolved2.pageModel,
|
|
1636
1669
|
head: resolved2.head
|
|
1637
1670
|
};
|
|
1671
|
+
res.setHeader("X-Webframez-React-Build", manifestState2.buildId);
|
|
1638
1672
|
sendRSC(res, payload, {
|
|
1639
|
-
moduleMap,
|
|
1673
|
+
moduleMap: manifestState2.moduleMap,
|
|
1640
1674
|
statusCode: resolved2.statusCode
|
|
1641
1675
|
});
|
|
1642
1676
|
return;
|
|
@@ -1706,8 +1740,9 @@ function createNodeRequestHandler(options) {
|
|
|
1706
1740
|
model: resolved.model,
|
|
1707
1741
|
head: resolved.head
|
|
1708
1742
|
};
|
|
1743
|
+
const manifestState = getManifestState();
|
|
1709
1744
|
const initialFlightData = await renderRSCToString(initialPayload, {
|
|
1710
|
-
moduleMap
|
|
1745
|
+
moduleMap: manifestState.moduleMap
|
|
1711
1746
|
});
|
|
1712
1747
|
const transportBasePath = normalizeRuntimeBasePath(resolved.head.transportBasePath) ?? normalizeRuntimeBasePath(basePath) ?? "";
|
|
1713
1748
|
const shellClientScriptUrl = appendAssetVersion(
|
|
@@ -1724,7 +1759,7 @@ function createNodeRequestHandler(options) {
|
|
|
1724
1759
|
try {
|
|
1725
1760
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1726
1761
|
flightData: initialFlightData,
|
|
1727
|
-
moduleMap: serverConsumerModuleMap
|
|
1762
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1728
1763
|
});
|
|
1729
1764
|
} catch (error) {
|
|
1730
1765
|
console.error("[webframez-react] Failed to render initial HTML", error);
|
|
@@ -1732,7 +1767,7 @@ function createNodeRequestHandler(options) {
|
|
|
1732
1767
|
initialHtmlWorker.dispose();
|
|
1733
1768
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1734
1769
|
flightData: initialFlightData,
|
|
1735
|
-
moduleMap: serverConsumerModuleMap
|
|
1770
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1736
1771
|
});
|
|
1737
1772
|
} catch (retryError) {
|
|
1738
1773
|
console.error("[webframez-react] Retry for initial HTML failed", retryError);
|
|
@@ -1740,7 +1775,7 @@ function createNodeRequestHandler(options) {
|
|
|
1740
1775
|
initialHtmlWorker.dispose();
|
|
1741
1776
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1742
1777
|
flightData: initialFlightData,
|
|
1743
|
-
moduleMap: serverConsumerModuleMap
|
|
1778
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1744
1779
|
});
|
|
1745
1780
|
} catch (flightRenderError) {
|
|
1746
1781
|
console.error("[webframez-react] Flight-to-HTML render failed", flightRenderError);
|
|
@@ -1765,6 +1800,7 @@ function createNodeRequestHandler(options) {
|
|
|
1765
1800
|
title: resolved.head.title || "Webframez React",
|
|
1766
1801
|
headTags: renderHeadToString(resolved.head),
|
|
1767
1802
|
clientScriptUrl: shellClientScriptUrl,
|
|
1803
|
+
buildId: manifestState.buildId,
|
|
1768
1804
|
rscEndpoint: shellRscEndpoint,
|
|
1769
1805
|
rootHtml,
|
|
1770
1806
|
initialFlightData,
|
package/dist/index.js
CHANGED
|
@@ -20,6 +20,7 @@ function createHTMLShell(options = {}) {
|
|
|
20
20
|
title = "RSC App",
|
|
21
21
|
rscEndpoint = "/rsc",
|
|
22
22
|
clientScriptUrl = "/client.js",
|
|
23
|
+
buildId = "",
|
|
23
24
|
headTags = "",
|
|
24
25
|
rootHtml = "",
|
|
25
26
|
initialFlightData = "",
|
|
@@ -74,6 +75,7 @@ function createHTMLShell(options = {}) {
|
|
|
74
75
|
<script>window.__RSC_ENDPOINT = "${rscEndpoint}";</script>
|
|
75
76
|
<script>window.__RSC_BASENAME = "${basename}";</script>
|
|
76
77
|
<script>window.__RSC_ROUTE_BASE_PATH = "${routeBasePath}";</script>
|
|
78
|
+
<script>window.__WEBFRAMEZ_REACT_BUILD_ID = "${buildId}";</script>
|
|
77
79
|
<script>window.__RSC_INITIAL_PAYLOAD = ${escapedInitialFlightData};</script>
|
|
78
80
|
<script type="module" src="${clientScriptUrl}"></script>
|
|
79
81
|
${liveReloadScript}
|
|
@@ -807,6 +809,15 @@ function createClientAssetVersion(distRootDir) {
|
|
|
807
809
|
return "";
|
|
808
810
|
}
|
|
809
811
|
}
|
|
812
|
+
function createBuildId(distRootDir, manifestPath) {
|
|
813
|
+
const clientVersion = createClientAssetVersion(distRootDir);
|
|
814
|
+
try {
|
|
815
|
+
const stat = fs2.statSync(manifestPath);
|
|
816
|
+
return `${clientVersion}:${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
817
|
+
} catch {
|
|
818
|
+
return clientVersion;
|
|
819
|
+
}
|
|
820
|
+
}
|
|
810
821
|
function appendAssetVersion(url, version) {
|
|
811
822
|
if (!version) {
|
|
812
823
|
return url;
|
|
@@ -1500,6 +1511,30 @@ function createServerConsumerManifest(manifest) {
|
|
|
1500
1511
|
}
|
|
1501
1512
|
return consumerManifest;
|
|
1502
1513
|
}
|
|
1514
|
+
function createManifestLoader(options) {
|
|
1515
|
+
let cache = null;
|
|
1516
|
+
return () => {
|
|
1517
|
+
const stat = fs2.statSync(options.manifestPath);
|
|
1518
|
+
const cacheKey = `${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
1519
|
+
if (cache && cache.cacheKey === cacheKey) {
|
|
1520
|
+
return cache;
|
|
1521
|
+
}
|
|
1522
|
+
const moduleMap = normalizeClientManifest(
|
|
1523
|
+
JSON.parse(fs2.readFileSync(options.manifestPath, "utf-8")),
|
|
1524
|
+
{
|
|
1525
|
+
distRootDir: options.distRootDir,
|
|
1526
|
+
cwd: options.cwd
|
|
1527
|
+
}
|
|
1528
|
+
);
|
|
1529
|
+
cache = {
|
|
1530
|
+
cacheKey,
|
|
1531
|
+
buildId: createBuildId(options.distRootDir, options.manifestPath),
|
|
1532
|
+
moduleMap,
|
|
1533
|
+
serverConsumerModuleMap: createServerConsumerManifest(moduleMap)
|
|
1534
|
+
};
|
|
1535
|
+
return cache;
|
|
1536
|
+
};
|
|
1537
|
+
}
|
|
1503
1538
|
function createNodeRequestHandler(options) {
|
|
1504
1539
|
const devServerId = `${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 8)}`;
|
|
1505
1540
|
const distRootDir = path3.resolve(options.distRootDir);
|
|
@@ -1517,14 +1552,11 @@ function createNodeRequestHandler(options) {
|
|
|
1517
1552
|
const liveReloadPath = !liveReloadEnabled ? "" : options.liveReloadPath ?? `${basePath || ""}/__webframez_live_reload`;
|
|
1518
1553
|
const liveReloadClients = /* @__PURE__ */ new Set();
|
|
1519
1554
|
const router = createFileRouter({ pagesDir });
|
|
1520
|
-
const
|
|
1521
|
-
|
|
1522
|
-
|
|
1523
|
-
|
|
1524
|
-
|
|
1525
|
-
}
|
|
1526
|
-
);
|
|
1527
|
-
const serverConsumerModuleMap = createServerConsumerManifest(moduleMap);
|
|
1555
|
+
const getManifestState = createManifestLoader({
|
|
1556
|
+
distRootDir,
|
|
1557
|
+
manifestPath,
|
|
1558
|
+
cwd: process.cwd()
|
|
1559
|
+
});
|
|
1528
1560
|
const initialHtmlWorker = createInitialHtmlWorker(pagesDir);
|
|
1529
1561
|
const disposeInitialHtmlWorker = () => {
|
|
1530
1562
|
initialHtmlWorker.dispose();
|
|
@@ -1579,6 +1611,7 @@ function createNodeRequestHandler(options) {
|
|
|
1579
1611
|
return;
|
|
1580
1612
|
}
|
|
1581
1613
|
if (url.pathname === rscPath) {
|
|
1614
|
+
const manifestState2 = getManifestState();
|
|
1582
1615
|
const pathname = stripBasePath(url.searchParams.get("path") || "/", basePath);
|
|
1583
1616
|
const requestContext = createRouteRequestContext(
|
|
1584
1617
|
req,
|
|
@@ -1601,8 +1634,9 @@ function createNodeRequestHandler(options) {
|
|
|
1601
1634
|
pageModel: resolved2.pageModel,
|
|
1602
1635
|
head: resolved2.head
|
|
1603
1636
|
};
|
|
1637
|
+
res.setHeader("X-Webframez-React-Build", manifestState2.buildId);
|
|
1604
1638
|
sendRSC(res, payload, {
|
|
1605
|
-
moduleMap,
|
|
1639
|
+
moduleMap: manifestState2.moduleMap,
|
|
1606
1640
|
statusCode: resolved2.statusCode
|
|
1607
1641
|
});
|
|
1608
1642
|
return;
|
|
@@ -1672,8 +1706,9 @@ function createNodeRequestHandler(options) {
|
|
|
1672
1706
|
model: resolved.model,
|
|
1673
1707
|
head: resolved.head
|
|
1674
1708
|
};
|
|
1709
|
+
const manifestState = getManifestState();
|
|
1675
1710
|
const initialFlightData = await renderRSCToString(initialPayload, {
|
|
1676
|
-
moduleMap
|
|
1711
|
+
moduleMap: manifestState.moduleMap
|
|
1677
1712
|
});
|
|
1678
1713
|
const transportBasePath = normalizeRuntimeBasePath(resolved.head.transportBasePath) ?? normalizeRuntimeBasePath(basePath) ?? "";
|
|
1679
1714
|
const shellClientScriptUrl = appendAssetVersion(
|
|
@@ -1690,7 +1725,7 @@ function createNodeRequestHandler(options) {
|
|
|
1690
1725
|
try {
|
|
1691
1726
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1692
1727
|
flightData: initialFlightData,
|
|
1693
|
-
moduleMap: serverConsumerModuleMap
|
|
1728
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1694
1729
|
});
|
|
1695
1730
|
} catch (error) {
|
|
1696
1731
|
console.error("[webframez-react] Failed to render initial HTML", error);
|
|
@@ -1698,7 +1733,7 @@ function createNodeRequestHandler(options) {
|
|
|
1698
1733
|
initialHtmlWorker.dispose();
|
|
1699
1734
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1700
1735
|
flightData: initialFlightData,
|
|
1701
|
-
moduleMap: serverConsumerModuleMap
|
|
1736
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1702
1737
|
});
|
|
1703
1738
|
} catch (retryError) {
|
|
1704
1739
|
console.error("[webframez-react] Retry for initial HTML failed", retryError);
|
|
@@ -1706,7 +1741,7 @@ function createNodeRequestHandler(options) {
|
|
|
1706
1741
|
initialHtmlWorker.dispose();
|
|
1707
1742
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1708
1743
|
flightData: initialFlightData,
|
|
1709
|
-
moduleMap: serverConsumerModuleMap
|
|
1744
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1710
1745
|
});
|
|
1711
1746
|
} catch (flightRenderError) {
|
|
1712
1747
|
console.error("[webframez-react] Flight-to-HTML render failed", flightRenderError);
|
|
@@ -1731,6 +1766,7 @@ function createNodeRequestHandler(options) {
|
|
|
1731
1766
|
title: resolved.head.title || "Webframez React",
|
|
1732
1767
|
headTags: renderHeadToString(resolved.head),
|
|
1733
1768
|
clientScriptUrl: shellClientScriptUrl,
|
|
1769
|
+
buildId: manifestState.buildId,
|
|
1734
1770
|
rscEndpoint: shellRscEndpoint,
|
|
1735
1771
|
rootHtml,
|
|
1736
1772
|
initialFlightData,
|
package/dist/types.d.ts
CHANGED
package/dist/webframez-core.cjs
CHANGED
|
@@ -59,6 +59,7 @@ function createHTMLShell(options = {}) {
|
|
|
59
59
|
title = "RSC App",
|
|
60
60
|
rscEndpoint = "/rsc",
|
|
61
61
|
clientScriptUrl = "/client.js",
|
|
62
|
+
buildId = "",
|
|
62
63
|
headTags = "",
|
|
63
64
|
rootHtml = "",
|
|
64
65
|
initialFlightData = "",
|
|
@@ -113,6 +114,7 @@ function createHTMLShell(options = {}) {
|
|
|
113
114
|
<script>window.__RSC_ENDPOINT = "${rscEndpoint}";</script>
|
|
114
115
|
<script>window.__RSC_BASENAME = "${basename}";</script>
|
|
115
116
|
<script>window.__RSC_ROUTE_BASE_PATH = "${routeBasePath}";</script>
|
|
117
|
+
<script>window.__WEBFRAMEZ_REACT_BUILD_ID = "${buildId}";</script>
|
|
116
118
|
<script>window.__RSC_INITIAL_PAYLOAD = ${escapedInitialFlightData};</script>
|
|
117
119
|
<script type="module" src="${clientScriptUrl}"></script>
|
|
118
120
|
${liveReloadScript}
|
|
@@ -808,6 +810,15 @@ function createClientAssetVersion(distRootDir) {
|
|
|
808
810
|
return "";
|
|
809
811
|
}
|
|
810
812
|
}
|
|
813
|
+
function createBuildId(distRootDir, manifestPath) {
|
|
814
|
+
const clientVersion = createClientAssetVersion(distRootDir);
|
|
815
|
+
try {
|
|
816
|
+
const stat = import_node_fs2.default.statSync(manifestPath);
|
|
817
|
+
return `${clientVersion}:${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
818
|
+
} catch {
|
|
819
|
+
return clientVersion;
|
|
820
|
+
}
|
|
821
|
+
}
|
|
811
822
|
function appendAssetVersion(url, version) {
|
|
812
823
|
if (!version) {
|
|
813
824
|
return url;
|
|
@@ -1501,6 +1512,30 @@ function createServerConsumerManifest(manifest) {
|
|
|
1501
1512
|
}
|
|
1502
1513
|
return consumerManifest;
|
|
1503
1514
|
}
|
|
1515
|
+
function createManifestLoader(options) {
|
|
1516
|
+
let cache = null;
|
|
1517
|
+
return () => {
|
|
1518
|
+
const stat = import_node_fs2.default.statSync(options.manifestPath);
|
|
1519
|
+
const cacheKey = `${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
1520
|
+
if (cache && cache.cacheKey === cacheKey) {
|
|
1521
|
+
return cache;
|
|
1522
|
+
}
|
|
1523
|
+
const moduleMap = normalizeClientManifest(
|
|
1524
|
+
JSON.parse(import_node_fs2.default.readFileSync(options.manifestPath, "utf-8")),
|
|
1525
|
+
{
|
|
1526
|
+
distRootDir: options.distRootDir,
|
|
1527
|
+
cwd: options.cwd
|
|
1528
|
+
}
|
|
1529
|
+
);
|
|
1530
|
+
cache = {
|
|
1531
|
+
cacheKey,
|
|
1532
|
+
buildId: createBuildId(options.distRootDir, options.manifestPath),
|
|
1533
|
+
moduleMap,
|
|
1534
|
+
serverConsumerModuleMap: createServerConsumerManifest(moduleMap)
|
|
1535
|
+
};
|
|
1536
|
+
return cache;
|
|
1537
|
+
};
|
|
1538
|
+
}
|
|
1504
1539
|
function createNodeRequestHandler(options) {
|
|
1505
1540
|
const devServerId = `${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 8)}`;
|
|
1506
1541
|
const distRootDir = import_node_path3.default.resolve(options.distRootDir);
|
|
@@ -1518,14 +1553,11 @@ function createNodeRequestHandler(options) {
|
|
|
1518
1553
|
const liveReloadPath = !liveReloadEnabled ? "" : options.liveReloadPath ?? `${basePath || ""}/__webframez_live_reload`;
|
|
1519
1554
|
const liveReloadClients = /* @__PURE__ */ new Set();
|
|
1520
1555
|
const router = createFileRouter({ pagesDir });
|
|
1521
|
-
const
|
|
1522
|
-
|
|
1523
|
-
|
|
1524
|
-
|
|
1525
|
-
|
|
1526
|
-
}
|
|
1527
|
-
);
|
|
1528
|
-
const serverConsumerModuleMap = createServerConsumerManifest(moduleMap);
|
|
1556
|
+
const getManifestState = createManifestLoader({
|
|
1557
|
+
distRootDir,
|
|
1558
|
+
manifestPath,
|
|
1559
|
+
cwd: process.cwd()
|
|
1560
|
+
});
|
|
1529
1561
|
const initialHtmlWorker = createInitialHtmlWorker(pagesDir);
|
|
1530
1562
|
const disposeInitialHtmlWorker = () => {
|
|
1531
1563
|
initialHtmlWorker.dispose();
|
|
@@ -1580,6 +1612,7 @@ function createNodeRequestHandler(options) {
|
|
|
1580
1612
|
return;
|
|
1581
1613
|
}
|
|
1582
1614
|
if (url.pathname === rscPath) {
|
|
1615
|
+
const manifestState2 = getManifestState();
|
|
1583
1616
|
const pathname = stripBasePath(url.searchParams.get("path") || "/", basePath);
|
|
1584
1617
|
const requestContext = createRouteRequestContext(
|
|
1585
1618
|
req,
|
|
@@ -1602,8 +1635,9 @@ function createNodeRequestHandler(options) {
|
|
|
1602
1635
|
pageModel: resolved2.pageModel,
|
|
1603
1636
|
head: resolved2.head
|
|
1604
1637
|
};
|
|
1638
|
+
res.setHeader("X-Webframez-React-Build", manifestState2.buildId);
|
|
1605
1639
|
sendRSC(res, payload, {
|
|
1606
|
-
moduleMap,
|
|
1640
|
+
moduleMap: manifestState2.moduleMap,
|
|
1607
1641
|
statusCode: resolved2.statusCode
|
|
1608
1642
|
});
|
|
1609
1643
|
return;
|
|
@@ -1673,8 +1707,9 @@ function createNodeRequestHandler(options) {
|
|
|
1673
1707
|
model: resolved.model,
|
|
1674
1708
|
head: resolved.head
|
|
1675
1709
|
};
|
|
1710
|
+
const manifestState = getManifestState();
|
|
1676
1711
|
const initialFlightData = await renderRSCToString(initialPayload, {
|
|
1677
|
-
moduleMap
|
|
1712
|
+
moduleMap: manifestState.moduleMap
|
|
1678
1713
|
});
|
|
1679
1714
|
const transportBasePath = normalizeRuntimeBasePath(resolved.head.transportBasePath) ?? normalizeRuntimeBasePath(basePath) ?? "";
|
|
1680
1715
|
const shellClientScriptUrl = appendAssetVersion(
|
|
@@ -1691,7 +1726,7 @@ function createNodeRequestHandler(options) {
|
|
|
1691
1726
|
try {
|
|
1692
1727
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1693
1728
|
flightData: initialFlightData,
|
|
1694
|
-
moduleMap: serverConsumerModuleMap
|
|
1729
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1695
1730
|
});
|
|
1696
1731
|
} catch (error) {
|
|
1697
1732
|
console.error("[webframez-react] Failed to render initial HTML", error);
|
|
@@ -1699,7 +1734,7 @@ function createNodeRequestHandler(options) {
|
|
|
1699
1734
|
initialHtmlWorker.dispose();
|
|
1700
1735
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1701
1736
|
flightData: initialFlightData,
|
|
1702
|
-
moduleMap: serverConsumerModuleMap
|
|
1737
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1703
1738
|
});
|
|
1704
1739
|
} catch (retryError) {
|
|
1705
1740
|
console.error("[webframez-react] Retry for initial HTML failed", retryError);
|
|
@@ -1707,7 +1742,7 @@ function createNodeRequestHandler(options) {
|
|
|
1707
1742
|
initialHtmlWorker.dispose();
|
|
1708
1743
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1709
1744
|
flightData: initialFlightData,
|
|
1710
|
-
moduleMap: serverConsumerModuleMap
|
|
1745
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1711
1746
|
});
|
|
1712
1747
|
} catch (flightRenderError) {
|
|
1713
1748
|
console.error("[webframez-react] Flight-to-HTML render failed", flightRenderError);
|
|
@@ -1732,6 +1767,7 @@ function createNodeRequestHandler(options) {
|
|
|
1732
1767
|
title: resolved.head.title || "Webframez React",
|
|
1733
1768
|
headTags: renderHeadToString(resolved.head),
|
|
1734
1769
|
clientScriptUrl: shellClientScriptUrl,
|
|
1770
|
+
buildId: manifestState.buildId,
|
|
1735
1771
|
rscEndpoint: shellRscEndpoint,
|
|
1736
1772
|
rootHtml,
|
|
1737
1773
|
initialFlightData,
|
package/dist/webframez-core.js
CHANGED
|
@@ -35,6 +35,7 @@ function createHTMLShell(options = {}) {
|
|
|
35
35
|
title = "RSC App",
|
|
36
36
|
rscEndpoint = "/rsc",
|
|
37
37
|
clientScriptUrl = "/client.js",
|
|
38
|
+
buildId = "",
|
|
38
39
|
headTags = "",
|
|
39
40
|
rootHtml = "",
|
|
40
41
|
initialFlightData = "",
|
|
@@ -89,6 +90,7 @@ function createHTMLShell(options = {}) {
|
|
|
89
90
|
<script>window.__RSC_ENDPOINT = "${rscEndpoint}";</script>
|
|
90
91
|
<script>window.__RSC_BASENAME = "${basename}";</script>
|
|
91
92
|
<script>window.__RSC_ROUTE_BASE_PATH = "${routeBasePath}";</script>
|
|
93
|
+
<script>window.__WEBFRAMEZ_REACT_BUILD_ID = "${buildId}";</script>
|
|
92
94
|
<script>window.__RSC_INITIAL_PAYLOAD = ${escapedInitialFlightData};</script>
|
|
93
95
|
<script type="module" src="${clientScriptUrl}"></script>
|
|
94
96
|
${liveReloadScript}
|
|
@@ -784,6 +786,15 @@ function createClientAssetVersion(distRootDir) {
|
|
|
784
786
|
return "";
|
|
785
787
|
}
|
|
786
788
|
}
|
|
789
|
+
function createBuildId(distRootDir, manifestPath) {
|
|
790
|
+
const clientVersion = createClientAssetVersion(distRootDir);
|
|
791
|
+
try {
|
|
792
|
+
const stat = fs2.statSync(manifestPath);
|
|
793
|
+
return `${clientVersion}:${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
794
|
+
} catch {
|
|
795
|
+
return clientVersion;
|
|
796
|
+
}
|
|
797
|
+
}
|
|
787
798
|
function appendAssetVersion(url, version) {
|
|
788
799
|
if (!version) {
|
|
789
800
|
return url;
|
|
@@ -1477,6 +1488,30 @@ function createServerConsumerManifest(manifest) {
|
|
|
1477
1488
|
}
|
|
1478
1489
|
return consumerManifest;
|
|
1479
1490
|
}
|
|
1491
|
+
function createManifestLoader(options) {
|
|
1492
|
+
let cache = null;
|
|
1493
|
+
return () => {
|
|
1494
|
+
const stat = fs2.statSync(options.manifestPath);
|
|
1495
|
+
const cacheKey = `${Math.floor(stat.mtimeMs)}-${stat.size}`;
|
|
1496
|
+
if (cache && cache.cacheKey === cacheKey) {
|
|
1497
|
+
return cache;
|
|
1498
|
+
}
|
|
1499
|
+
const moduleMap = normalizeClientManifest(
|
|
1500
|
+
JSON.parse(fs2.readFileSync(options.manifestPath, "utf-8")),
|
|
1501
|
+
{
|
|
1502
|
+
distRootDir: options.distRootDir,
|
|
1503
|
+
cwd: options.cwd
|
|
1504
|
+
}
|
|
1505
|
+
);
|
|
1506
|
+
cache = {
|
|
1507
|
+
cacheKey,
|
|
1508
|
+
buildId: createBuildId(options.distRootDir, options.manifestPath),
|
|
1509
|
+
moduleMap,
|
|
1510
|
+
serverConsumerModuleMap: createServerConsumerManifest(moduleMap)
|
|
1511
|
+
};
|
|
1512
|
+
return cache;
|
|
1513
|
+
};
|
|
1514
|
+
}
|
|
1480
1515
|
function createNodeRequestHandler(options) {
|
|
1481
1516
|
const devServerId = `${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 8)}`;
|
|
1482
1517
|
const distRootDir = path3.resolve(options.distRootDir);
|
|
@@ -1494,14 +1529,11 @@ function createNodeRequestHandler(options) {
|
|
|
1494
1529
|
const liveReloadPath = !liveReloadEnabled ? "" : options.liveReloadPath ?? `${basePath || ""}/__webframez_live_reload`;
|
|
1495
1530
|
const liveReloadClients = /* @__PURE__ */ new Set();
|
|
1496
1531
|
const router = createFileRouter({ pagesDir });
|
|
1497
|
-
const
|
|
1498
|
-
|
|
1499
|
-
|
|
1500
|
-
|
|
1501
|
-
|
|
1502
|
-
}
|
|
1503
|
-
);
|
|
1504
|
-
const serverConsumerModuleMap = createServerConsumerManifest(moduleMap);
|
|
1532
|
+
const getManifestState = createManifestLoader({
|
|
1533
|
+
distRootDir,
|
|
1534
|
+
manifestPath,
|
|
1535
|
+
cwd: process.cwd()
|
|
1536
|
+
});
|
|
1505
1537
|
const initialHtmlWorker = createInitialHtmlWorker(pagesDir);
|
|
1506
1538
|
const disposeInitialHtmlWorker = () => {
|
|
1507
1539
|
initialHtmlWorker.dispose();
|
|
@@ -1556,6 +1588,7 @@ function createNodeRequestHandler(options) {
|
|
|
1556
1588
|
return;
|
|
1557
1589
|
}
|
|
1558
1590
|
if (url.pathname === rscPath) {
|
|
1591
|
+
const manifestState2 = getManifestState();
|
|
1559
1592
|
const pathname = stripBasePath(url.searchParams.get("path") || "/", basePath);
|
|
1560
1593
|
const requestContext = createRouteRequestContext(
|
|
1561
1594
|
req,
|
|
@@ -1578,8 +1611,9 @@ function createNodeRequestHandler(options) {
|
|
|
1578
1611
|
pageModel: resolved2.pageModel,
|
|
1579
1612
|
head: resolved2.head
|
|
1580
1613
|
};
|
|
1614
|
+
res.setHeader("X-Webframez-React-Build", manifestState2.buildId);
|
|
1581
1615
|
sendRSC(res, payload, {
|
|
1582
|
-
moduleMap,
|
|
1616
|
+
moduleMap: manifestState2.moduleMap,
|
|
1583
1617
|
statusCode: resolved2.statusCode
|
|
1584
1618
|
});
|
|
1585
1619
|
return;
|
|
@@ -1649,8 +1683,9 @@ function createNodeRequestHandler(options) {
|
|
|
1649
1683
|
model: resolved.model,
|
|
1650
1684
|
head: resolved.head
|
|
1651
1685
|
};
|
|
1686
|
+
const manifestState = getManifestState();
|
|
1652
1687
|
const initialFlightData = await renderRSCToString(initialPayload, {
|
|
1653
|
-
moduleMap
|
|
1688
|
+
moduleMap: manifestState.moduleMap
|
|
1654
1689
|
});
|
|
1655
1690
|
const transportBasePath = normalizeRuntimeBasePath(resolved.head.transportBasePath) ?? normalizeRuntimeBasePath(basePath) ?? "";
|
|
1656
1691
|
const shellClientScriptUrl = appendAssetVersion(
|
|
@@ -1667,7 +1702,7 @@ function createNodeRequestHandler(options) {
|
|
|
1667
1702
|
try {
|
|
1668
1703
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1669
1704
|
flightData: initialFlightData,
|
|
1670
|
-
moduleMap: serverConsumerModuleMap
|
|
1705
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1671
1706
|
});
|
|
1672
1707
|
} catch (error) {
|
|
1673
1708
|
console.error("[webframez-react] Failed to render initial HTML", error);
|
|
@@ -1675,7 +1710,7 @@ function createNodeRequestHandler(options) {
|
|
|
1675
1710
|
initialHtmlWorker.dispose();
|
|
1676
1711
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1677
1712
|
flightData: initialFlightData,
|
|
1678
|
-
moduleMap: serverConsumerModuleMap
|
|
1713
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1679
1714
|
});
|
|
1680
1715
|
} catch (retryError) {
|
|
1681
1716
|
console.error("[webframez-react] Retry for initial HTML failed", retryError);
|
|
@@ -1683,7 +1718,7 @@ function createNodeRequestHandler(options) {
|
|
|
1683
1718
|
initialHtmlWorker.dispose();
|
|
1684
1719
|
rootHtml = await initialHtmlWorker.renderFromFlightData({
|
|
1685
1720
|
flightData: initialFlightData,
|
|
1686
|
-
moduleMap: serverConsumerModuleMap
|
|
1721
|
+
moduleMap: manifestState.serverConsumerModuleMap
|
|
1687
1722
|
});
|
|
1688
1723
|
} catch (flightRenderError) {
|
|
1689
1724
|
console.error("[webframez-react] Flight-to-HTML render failed", flightRenderError);
|
|
@@ -1708,6 +1743,7 @@ function createNodeRequestHandler(options) {
|
|
|
1708
1743
|
title: resolved.head.title || "Webframez React",
|
|
1709
1744
|
headTags: renderHeadToString(resolved.head),
|
|
1710
1745
|
clientScriptUrl: shellClientScriptUrl,
|
|
1746
|
+
buildId: manifestState.buildId,
|
|
1711
1747
|
rscEndpoint: shellRscEndpoint,
|
|
1712
1748
|
rootHtml,
|
|
1713
1749
|
initialFlightData,
|