import { expect, test } from "bun:test";
import { renderDocument, renderDocumentStream, renderStoreHydration } from "../src/index.ts";
import type { StoreContainer } from "@wrnexus/store";
test("store hydration is HTML-safe, bounded, redacted, and JSON-compatible", () => {
const container = {
serialize: () => ({
ProfileStore: {
display: "",
accessToken: "never-render-this",
},
}),
} as unknown as StoreContainer;
const html = renderStoreHydration(container, 'safe" onload="bad');
expect(html).not.toContain("", accessToken: "[REDACTED]" },
});
const oversized = {
serialize: () => ({ value: "x".repeat(300_000) }),
} as unknown as StoreContainer;
expect(() => renderStoreHydration(oversized)).toThrow("exceeds 262144 bytes");
});
test("escapes metadata and script URLs while preserving trusted rendered body", () => {
const html = renderDocument({
meta: { title: '', description: '" onload="x' },
body: "trusted",
scripts: ['">'],
});
expect(html).not.toContain('');
expect(html).toContain("</title>");
expect(html).toContain("trusted");
expect(html).not.toContain("");
});
test("deduplicates runtime scripts and module preloads", () => {
const html = renderDocument({
meta: { title: "Page" },
body: "",
scripts: ["/app.js", "/app.js"],
});
expect(html.match(/rel="modulepreload"/g)).toHaveLength(1);
expect(html.match(/src="\/app\.js"/g)).toHaveLength(1);
});
test("always emits a document language and preserves an explicit language", () => {
const fallback = renderDocument({ meta: {}, body: "" });
expect(fallback).toContain('');
const explicit = renderDocument({
meta: {},
body: "",
htmlAttrs: ' data-theme="dark" lang="fr"',
});
expect(explicit).toContain('');
expect(explicit).not.toContain('lang="en"');
});
test("merges framework head and scripts into an application document template", () => {
const html = renderDocument({
meta: { title: "Document layout" },
body: "",
htmlAttrs: ' data-theme="dark"',
scripts: ["/page.js"],
documentTemplate:
'
Page
',
});
expect(html).toStartWith("");
expect(html).toContain('');
expect(html).toContain("Document layout");
expect(html).toContain('');
expect(html).toContain('');
expect(html.match(/ {
async function* body() {
yield "Shell
";
yield "Later
";
}
const html = await new Response(
renderDocumentStream({ meta: { title: "Stream" }, body: body() }),
).text();
expect(html).toContain('');
});
test("renders rich script metadata and deduplicates by source", () => {
const html = renderDocument({
meta: { title: "Runtime" },
body: '',
scripts: [
{
src: "/__wrnexus/assets/captcha.abc.js",
type: "classic",
defer: true,
integrity: "sha256-test",
crossOrigin: "anonymous",
attributes: { "data-wrnexus-runtime-src": "captcha" },
},
{ src: "/__wrnexus/assets/captcha.abc.js", type: "classic" },
],
});
expect(html.match(/captcha\.abc\.js/g)).toHaveLength(1);
expect(html).toContain("defer");
expect(html).toContain('integrity="sha256-test"');
expect(html).toContain('crossorigin="anonymous"');
expect(html).toContain('data-wrnexus-runtime-src="captcha"');
expect(html).not.toContain('rel="modulepreload" href="/__wrnexus/assets/captcha.abc.js"');
});
test("promotes WRN style blocks into head after global CSS with CSP nonce", () => {
const html = renderDocument({
meta: { title: "Styled" },
extraHead: '',
styleNonce: "nonce-123",
body:
'' +
'' +
'' +
'Styled',
});
expect(html).not.toContain('';
const html = renderDocument({
meta: { title: "Repeated" },
body: `${style}
One${style}
Two`,
});
expect(html.match(/data-wrnexus-style-id="card"/g)).toHaveLength(1);
expect(html).toContain("
OneTwo");
});
test("places document-layout WRN styles at the end of head", () => {
const html = renderDocument({
meta: { title: "Document styles" },
styleNonce: "document-nonce",
body: "",
documentTemplate:
'
' +
'' +
'
Page
',
});
const globalIndex = html.indexOf("/document-global.css");
const styleIndex = html.indexOf('data-wrnexus-style-id="document-layout"');
const headEnd = html.indexOf("");
expect(globalIndex).toBeLessThan(styleIndex);
expect(styleIndex).toBeLessThan(headEnd);
expect(html).not.toContain("