perf: optimize production assets and proxy-aware URLs
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/ai",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "Zero-dependency Claude (Anthropic) client for WrNexus apps.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/authz",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/authz — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
+11
-11
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/cli",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/cli — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -28,16 +28,16 @@
|
||||
"wrnexus": "./dist/index.js"
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/core": "^0.2.14",
|
||||
"@wrnexus/router": "^0.2.14",
|
||||
"@wrnexus/csr": "^0.2.14",
|
||||
"@wrnexus/compiler": "^0.2.14",
|
||||
"@wrnexus/styles": "^0.2.14",
|
||||
"@wrnexus/dev-server": "^0.2.14",
|
||||
"@wrnexus/ui": "^0.2.14",
|
||||
"@wrnexus/validation": "^0.2.14",
|
||||
"@wrnexus/i18n": "^0.2.14",
|
||||
"@wrnexus/db": "^0.2.14"
|
||||
"@wrnexus/core": "^0.2.15",
|
||||
"@wrnexus/router": "^0.2.15",
|
||||
"@wrnexus/csr": "^0.2.15",
|
||||
"@wrnexus/compiler": "^0.2.15",
|
||||
"@wrnexus/styles": "^0.2.15",
|
||||
"@wrnexus/dev-server": "^0.2.15",
|
||||
"@wrnexus/ui": "^0.2.15",
|
||||
"@wrnexus/validation": "^0.2.15",
|
||||
"@wrnexus/i18n": "^0.2.15",
|
||||
"@wrnexus/db": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/compiler",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/compiler — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/core",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/core — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/csr",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/csr — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -21,7 +21,7 @@
|
||||
}
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/core": "^0.2.14"
|
||||
"@wrnexus/core": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/db",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/db — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/dev-server",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/dev-server — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -25,18 +25,18 @@
|
||||
}
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/core": "^0.2.14",
|
||||
"@wrnexus/router": "^0.2.14",
|
||||
"@wrnexus/ssr": "^0.2.14",
|
||||
"@wrnexus/csr": "^0.2.14",
|
||||
"@wrnexus/compiler": "^0.2.14",
|
||||
"@wrnexus/styles": "^0.2.14",
|
||||
"@wrnexus/ui": "^0.2.14",
|
||||
"@wrnexus/validation": "^0.2.14",
|
||||
"@wrnexus/i18n": "^0.2.14",
|
||||
"@wrnexus/db": "^0.2.14",
|
||||
"@wrnexus/pubsub": "^0.2.14",
|
||||
"@wrnexus/uploader": "^0.2.14"
|
||||
"@wrnexus/core": "^0.2.15",
|
||||
"@wrnexus/router": "^0.2.15",
|
||||
"@wrnexus/ssr": "^0.2.15",
|
||||
"@wrnexus/csr": "^0.2.15",
|
||||
"@wrnexus/compiler": "^0.2.15",
|
||||
"@wrnexus/styles": "^0.2.15",
|
||||
"@wrnexus/ui": "^0.2.15",
|
||||
"@wrnexus/validation": "^0.2.15",
|
||||
"@wrnexus/i18n": "^0.2.15",
|
||||
"@wrnexus/db": "^0.2.15",
|
||||
"@wrnexus/pubsub": "^0.2.15",
|
||||
"@wrnexus/uploader": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/encryption",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/encryption — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/i18n",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/i18n — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -21,7 +21,7 @@
|
||||
}
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/core": "^0.2.14"
|
||||
"@wrnexus/core": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/jwt",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/jwt — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/mobile",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/mobile — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -21,7 +21,7 @@
|
||||
}
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/native": "^0.2.14"
|
||||
"@wrnexus/native": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/native",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/native — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/oauth",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/oauth — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/pubsub",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/pubsub — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/queue",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/queue — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/reactive",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/reactive — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/router",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/router — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -21,8 +21,8 @@
|
||||
}
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/compiler": "^0.2.14",
|
||||
"@wrnexus/core": "^0.2.14"
|
||||
"@wrnexus/compiler": "^0.2.15",
|
||||
"@wrnexus/core": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/ssr",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/ssr — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -21,7 +21,7 @@
|
||||
}
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/core": "^0.2.14"
|
||||
"@wrnexus/core": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/styles",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/styles — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -21,7 +21,7 @@
|
||||
}
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/uploader": "^0.2.14"
|
||||
"@wrnexus/uploader": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/test",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/test — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/tracking",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/tracking — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/ui",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/ui — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -22,7 +22,7 @@
|
||||
"./ui.css": "./ui.css"
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/core": "^0.2.14"
|
||||
"@wrnexus/core": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/uploader",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/uploader — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
@@ -21,7 +21,7 @@
|
||||
}
|
||||
},
|
||||
"dependencies": {
|
||||
"@wrnexus/core": "^0.2.14"
|
||||
"@wrnexus/core": "^0.2.15"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/validation",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"description": "@wrnexus/validation — part of the WrNexus framework.",
|
||||
"license": "MIT",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/ai",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"description": "Zero-dependency Claude (Anthropic) client for WrNexus apps.",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/authz",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/cli",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -158,10 +158,13 @@ export async function runBuild(appRoot: string): Promise<void> {
|
||||
config.styles,
|
||||
);
|
||||
assetHash.update(css);
|
||||
writeFileSync(join(distDir, "styles.css"), css, "utf8");
|
||||
const combinedCss = `${frameworkStyles}\n${css}`;
|
||||
// One blocking CSS request in production: tokens → UI → application CSS.
|
||||
// The standalone framework.css remains available for apps without global CSS.
|
||||
writeFileSync(join(distDir, "styles.css"), combinedCss, "utf8");
|
||||
hasStyles = true;
|
||||
if (Buffer.byteLength(css, "utf8") <= INLINE_CSS_LIMIT_BYTES) {
|
||||
inlineStyles = css;
|
||||
if (Buffer.byteLength(combinedCss, "utf8") <= INLINE_CSS_LIMIT_BYTES) {
|
||||
inlineStyles = combinedCss;
|
||||
}
|
||||
console.log(`✓ Styles: ${join(distDir, "styles.css")}`);
|
||||
}
|
||||
@@ -254,6 +257,7 @@ await createProductionServer(
|
||||
realtime: ${config.realtime ? JSON.stringify(config.realtime) : "undefined"},
|
||||
publicDir: join(import.meta.dir, "public"),
|
||||
${hasStyles ? `stylesPath: join(import.meta.dir, "styles.css"),` : ""}
|
||||
${hasStyles ? `stylesIncludeFramework: true,` : ""}
|
||||
${inlineStyles ? `inlineStyles: ${JSON.stringify(inlineStyles)},` : ""}
|
||||
assetVersion: ${JSON.stringify(assetVersion)},
|
||||
head: ${JSON.stringify(headStr)},
|
||||
|
||||
@@ -205,6 +205,8 @@ const config: AppConfig = {
|
||||
seo: {
|
||||
title: "APP_NAME",
|
||||
titleTemplate: "%s | APP_NAME",
|
||||
// Set WRNEXUS_PUBLIC_ORIGIN in production when TLS terminates at a proxy.
|
||||
canonicalBase: process.env.WRNEXUS_PUBLIC_ORIGIN,
|
||||
description: "An SSR-first WrNexus app.",
|
||||
robots: "index,follow",
|
||||
themeColor: "#6366f1",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/compiler",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/core",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -178,9 +178,12 @@ export function createCorsPreflightResponse(
|
||||
export function resolveRequestUrl(req: Request, trustProxy?: boolean): URL {
|
||||
const url = new URL(req.url);
|
||||
if (!trustProxy) return url;
|
||||
const proto = req.headers.get("x-forwarded-proto");
|
||||
const forwarded = req.headers.get("forwarded")?.split(",")[0] ?? "";
|
||||
const forwardedProto = /(?:^|;)\s*proto=(?:"([^"]+)"|([^;\s]+))/i.exec(forwarded);
|
||||
const forwardedHost = /(?:^|;)\s*host=(?:"([^"]+)"|([^;\s]+))/i.exec(forwarded);
|
||||
const proto = req.headers.get("x-forwarded-proto") ?? forwardedProto?.[1] ?? forwardedProto?.[2];
|
||||
if (proto) url.protocol = (proto.split(",")[0] ?? "").trim() + ":";
|
||||
const host = req.headers.get("x-forwarded-host");
|
||||
const host = req.headers.get("x-forwarded-host") ?? forwardedHost?.[1] ?? forwardedHost?.[2];
|
||||
if (host) {
|
||||
const h = (host.split(",")[0] ?? "").trim();
|
||||
url.host = h;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { test, expect } from "bun:test";
|
||||
import { withSecurityHeaders, isWebSocketOriginAllowed } from "../src/index.ts";
|
||||
import { withSecurityHeaders, isWebSocketOriginAllowed, resolveRequestUrl } from "../src/index.ts";
|
||||
|
||||
const req = (headers: Record<string, string> = {}) => new Request("https://x/", { headers });
|
||||
|
||||
@@ -64,3 +64,11 @@ test("isWebSocketOriginAllowed blocks cross-site WS (CSWSH), allows same-origin"
|
||||
}),
|
||||
).toBe(true);
|
||||
});
|
||||
|
||||
test("resolveRequestUrl honors standard Forwarded headers behind trusted proxies", () => {
|
||||
const request = new Request("http://127.0.0.1:3000/path", {
|
||||
headers: { forwarded: 'for=192.0.2.1;proto=https;host="workroot.in"' },
|
||||
});
|
||||
expect(resolveRequestUrl(request, true).href).toBe("https://workroot.in/path");
|
||||
expect(resolveRequestUrl(request, false).href).toBe("http://127.0.0.1:3000/path");
|
||||
});
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/csr",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/db",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/dev-server",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -65,6 +65,8 @@ export interface ProdOptions {
|
||||
stylesPath?: string;
|
||||
/** Small production stylesheet inlined into the document head. */
|
||||
inlineStyles?: string;
|
||||
/** `stylesPath` contains theme + UI + app CSS in cascade order. */
|
||||
stylesIncludeFramework?: boolean;
|
||||
/** Absolute path to the pre-built reactive runtime. */
|
||||
reactivePath?: string;
|
||||
/** Absolute path to the pre-built theme stylesheet (`theme.css`). */
|
||||
@@ -287,6 +289,7 @@ export function createProductionHandlers(
|
||||
theme: opts.theme,
|
||||
i18n: opts.i18n,
|
||||
inlineStyles: opts.inlineStyles,
|
||||
stylesIncludeFramework: opts.stylesIncludeFramework,
|
||||
assetVersion: opts.assetVersion,
|
||||
head: opts.head,
|
||||
seo: opts.seo,
|
||||
|
||||
@@ -33,6 +33,9 @@ function cachePolicy(filePath: string, mode: Mode): string {
|
||||
if (mode !== "production") return "no-cache";
|
||||
const name = filePath.split(/[\\/]/).pop() ?? "";
|
||||
if (/\.html?$/i.test(name)) return REVALIDATE_CACHE;
|
||||
// Font URLs are content assets with expensive transfer costs and are almost
|
||||
// always renamed when changed. Cache them like fingerprinted build assets.
|
||||
if (/\.(?:woff2?|ttf|otf|eot)$/i.test(name)) return IMMUTABLE_CACHE;
|
||||
return /(?:^|[.-])[a-f0-9]{8,}(?:[.-]|$)/i.test(name) ? IMMUTABLE_CACHE : "public, max-age=3600";
|
||||
}
|
||||
|
||||
|
||||
@@ -103,6 +103,8 @@ export interface RuntimeDeps {
|
||||
hasUi?: boolean;
|
||||
/** Production build combined theme + UI stylesheet. */
|
||||
hasFrameworkStyles?: boolean;
|
||||
/** App stylesheet already contains theme + UI CSS and is the only CSS request needed. */
|
||||
stylesIncludeFramework?: boolean;
|
||||
/** Resolved theme config: enables `/__wrnexus/theme.css` + `<html data-theme>`. */
|
||||
theme?: ResolvedTheme;
|
||||
/** Resolved i18n bundle: enables `ctx.t`, `<html lang>`, and `{t:key}` markers. */
|
||||
@@ -569,15 +571,15 @@ export function createHandlers(deps: RuntimeDeps): Handlers {
|
||||
// Order: theme tokens, then Wire UI, then the app stylesheet — so the app's
|
||||
// own CSS (loaded last) can override both the tokens and the UI classes.
|
||||
const headParts: string[] = [];
|
||||
if (deps.hasFrameworkStyles) {
|
||||
if (deps.hasFrameworkStyles && !deps.stylesIncludeFramework) {
|
||||
headParts.push(
|
||||
`<link rel="stylesheet" href="${versionAssetUrl("/__wrnexus/framework.css", deps.assetVersion)}" />`,
|
||||
);
|
||||
} else if (deps.theme) {
|
||||
} else if (deps.theme && !deps.stylesIncludeFramework) {
|
||||
const themeHref = versionAssetUrl(THEME_CSS_HREF, deps.assetVersion);
|
||||
headParts.push(`<link rel="stylesheet" href="${themeHref}" />`);
|
||||
}
|
||||
if (deps.hasUi && !deps.hasFrameworkStyles) {
|
||||
if (deps.hasUi && !deps.hasFrameworkStyles && !deps.stylesIncludeFramework) {
|
||||
headParts.push(
|
||||
`<link rel="stylesheet" href="${versionAssetUrl("/__wrnexus/ui.css", deps.assetVersion)}" />`,
|
||||
);
|
||||
|
||||
@@ -9,11 +9,14 @@ test("production HTML revalidates while fingerprinted assets are immutable", asy
|
||||
mkdirSync(join(root, "assets"));
|
||||
writeFileSync(join(root, "index.html"), "home");
|
||||
writeFileSync(join(root, "assets", "app.abcdef1234.js"), "app");
|
||||
writeFileSync(join(root, "brand.woff2"), "font");
|
||||
const html = await servePublicAsset(root, "/index.html", "production");
|
||||
const asset = await servePublicAsset(root, "/assets/app.abcdef1234.js", "production");
|
||||
const font = await servePublicAsset(root, "/brand.woff2", "production");
|
||||
expect(html?.headers.get("cache-control")).toBe("public, max-age=0, must-revalidate");
|
||||
expect(asset?.headers.get("cache-control")).toBe("public, max-age=31536000, immutable");
|
||||
expect(asset?.headers.get("x-content-type-options")).toBe("nosniff");
|
||||
expect(font?.headers.get("cache-control")).toBe("public, max-age=31536000, immutable");
|
||||
});
|
||||
|
||||
test("public server rejects encoded traversal", async () => {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/encryption",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/i18n",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/jwt",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/mobile",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/native",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/oauth",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/pubsub",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/queue",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/reactive",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/router",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/ssr",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/styles",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
"exports": {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/test",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/tracking",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/ui",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/uploader",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@wrnexus/validation",
|
||||
"version": "0.2.14",
|
||||
"version": "0.2.15",
|
||||
"private": true,
|
||||
"type": "module",
|
||||
"main": "src/index.ts",
|
||||
|
||||
Reference in New Issue
Block a user