@blinkk/root 3.0.5 → 3.1.1
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/build-worker.js +108 -0
- package/dist/build-worker.js.map +7 -0
- package/dist/chunk-3PWR4F2R.js +77 -0
- package/dist/chunk-3PWR4F2R.js.map +7 -0
- package/dist/{chunk-VQPDCDKL.js → chunk-E4F6CMO3.js} +469 -536
- package/dist/chunk-E4F6CMO3.js.map +7 -0
- package/dist/{chunk-6P3B7ZXL.js → chunk-I3RCAIW7.js} +1 -62
- package/dist/chunk-I3RCAIW7.js.map +7 -0
- package/dist/chunk-KHO3HMX6.js +291 -0
- package/dist/chunk-KHO3HMX6.js.map +7 -0
- package/dist/chunk-M3E4RKS7.js +374 -0
- package/dist/chunk-M3E4RKS7.js.map +7 -0
- package/dist/{chunk-6NBKAR5Y.js → chunk-TM6QRBGS.js} +31 -1
- package/dist/chunk-TM6QRBGS.js.map +7 -0
- package/dist/chunk-WX62JK5E.js +81 -0
- package/dist/chunk-WX62JK5E.js.map +7 -0
- package/dist/{chunk-7PSEEE6C.js → chunk-YU22SAIG.js} +31 -317
- package/dist/chunk-YU22SAIG.js.map +7 -0
- package/dist/cli/build-page.d.ts +57 -0
- package/dist/cli/build-worker-pool.d.ts +46 -0
- package/dist/cli/build-worker.d.ts +4 -0
- package/dist/cli/build.d.ts +6 -0
- package/dist/cli.js +8 -4
- package/dist/core/config.d.ts +11 -3
- package/dist/core/security.d.ts +14 -0
- package/dist/core.js.map +2 -2
- package/dist/functions.js +8 -4
- package/dist/functions.js.map +1 -1
- package/dist/jsx/types.d.ts +1 -0
- package/dist/middleware/common.d.ts +18 -0
- package/dist/middleware/compression.d.ts +12 -0
- package/dist/middleware/middleware.d.ts +1 -0
- package/dist/middleware.js +6 -1
- package/dist/node.js +7 -5
- package/dist/render/asset-map/build-asset-map.d.ts +11 -1
- package/dist/render/html-transform.d.ts +15 -0
- package/dist/render/render.d.ts +15 -9
- package/dist/render.js +45 -104
- package/dist/render.js.map +2 -2
- package/package.json +2 -2
- package/dist/chunk-6NBKAR5Y.js.map +0 -7
- package/dist/chunk-6P3B7ZXL.js.map +0 -7
- package/dist/chunk-7PSEEE6C.js.map +0 -7
- package/dist/chunk-VQPDCDKL.js.map +0 -7
package/dist/render.js
CHANGED
|
@@ -7,15 +7,20 @@ import {
|
|
|
7
7
|
testPathHasParams
|
|
8
8
|
} from "./chunk-KW7KTYGC.js";
|
|
9
9
|
import {
|
|
10
|
-
RouteTrie
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
parseTagNames
|
|
14
|
-
|
|
10
|
+
RouteTrie
|
|
11
|
+
} from "./chunk-I3RCAIW7.js";
|
|
12
|
+
import {
|
|
13
|
+
parseTagNames,
|
|
14
|
+
transformHtml
|
|
15
|
+
} from "./chunk-3PWR4F2R.js";
|
|
15
16
|
import {
|
|
16
17
|
renderJsxToString
|
|
17
18
|
} from "./chunk-X2C2MEJ2.js";
|
|
18
19
|
import "./chunk-3Z5TNZEP.js";
|
|
20
|
+
import {
|
|
21
|
+
getSecurityConfig,
|
|
22
|
+
setSecurityHeaders
|
|
23
|
+
} from "./chunk-WX62JK5E.js";
|
|
19
24
|
|
|
20
25
|
// src/render/render.tsx
|
|
21
26
|
import crypto from "node:crypto";
|
|
@@ -13120,6 +13125,14 @@ var Renderer = class {
|
|
|
13120
13125
|
getRoute(url) {
|
|
13121
13126
|
return this.router.get(url);
|
|
13122
13127
|
}
|
|
13128
|
+
/** Returns all routes that match a given url path. */
|
|
13129
|
+
getRouteMatches(url) {
|
|
13130
|
+
return this.router.matchAll(url);
|
|
13131
|
+
}
|
|
13132
|
+
/** Walks all routes registered with the router. */
|
|
13133
|
+
async walkRoutes(cb) {
|
|
13134
|
+
await this.router.walk(cb);
|
|
13135
|
+
}
|
|
13123
13136
|
async handle(req, res, next) {
|
|
13124
13137
|
let url = req.path;
|
|
13125
13138
|
if (url.includes("%")) {
|
|
@@ -13171,6 +13184,7 @@ var Renderer = class {
|
|
|
13171
13184
|
scriptDeps: []
|
|
13172
13185
|
};
|
|
13173
13186
|
const vdom = /* @__PURE__ */ jsx4(REQUEST_CONTEXT.Provider, { value: ctx, children: /* @__PURE__ */ jsx4(I18N_CONTEXT.Provider, { value: { locale, translations }, children: /* @__PURE__ */ jsx4(HTML_CONTEXT.Provider, { value: htmlContext, children: /* @__PURE__ */ jsx4(Component, { ...props }) }) }) });
|
|
13187
|
+
const renderJsxFn = await this.getJsxRenderFn();
|
|
13174
13188
|
const preactHook = preactOptions.vnode;
|
|
13175
13189
|
let mainHtml;
|
|
13176
13190
|
try {
|
|
@@ -13188,11 +13202,9 @@ var Renderer = class {
|
|
|
13188
13202
|
preactHook(vnode);
|
|
13189
13203
|
}
|
|
13190
13204
|
};
|
|
13191
|
-
mainHtml =
|
|
13192
|
-
|
|
13193
|
-
} catch (err) {
|
|
13205
|
+
mainHtml = renderJsxFn(vdom);
|
|
13206
|
+
} finally {
|
|
13194
13207
|
preactOptions.vnode = preactHook;
|
|
13195
|
-
throw err;
|
|
13196
13208
|
}
|
|
13197
13209
|
const jsDeps = /* @__PURE__ */ new Set();
|
|
13198
13210
|
const cssDeps = /* @__PURE__ */ new Set();
|
|
@@ -13322,7 +13334,7 @@ var Renderer = class {
|
|
|
13322
13334
|
render404();
|
|
13323
13335
|
return;
|
|
13324
13336
|
}
|
|
13325
|
-
const securityConfig = this.
|
|
13337
|
+
const securityConfig = getSecurityConfig(this.rootConfig);
|
|
13326
13338
|
const cspEnabled = !!securityConfig.contentSecurityPolicy;
|
|
13327
13339
|
const currentPath = req.path;
|
|
13328
13340
|
const locale = options2?.locale || route.locale;
|
|
@@ -13336,12 +13348,7 @@ var Renderer = class {
|
|
|
13336
13348
|
translations,
|
|
13337
13349
|
nonce
|
|
13338
13350
|
});
|
|
13339
|
-
let html = output.html;
|
|
13340
|
-
if (this.rootConfig.prettyHtml) {
|
|
13341
|
-
html = await htmlPretty(html, this.rootConfig.prettyHtmlOptions);
|
|
13342
|
-
} else if (this.rootConfig.minifyHtml !== false) {
|
|
13343
|
-
html = await htmlMinify(html, this.rootConfig.minifyHtmlOptions);
|
|
13344
|
-
}
|
|
13351
|
+
let html = await transformHtml(output.html, this.rootConfig);
|
|
13345
13352
|
if (req.viteServer) {
|
|
13346
13353
|
html = await req.viteServer.transformIndexHtml(currentPath, html);
|
|
13347
13354
|
if (nonce) {
|
|
@@ -13371,7 +13378,7 @@ var Renderer = class {
|
|
|
13371
13378
|
}
|
|
13372
13379
|
res.status(statusCode);
|
|
13373
13380
|
res.set({ "Content-Type": "text/html" });
|
|
13374
|
-
|
|
13381
|
+
setSecurityHeaders(res, {
|
|
13375
13382
|
securityConfig,
|
|
13376
13383
|
nonce
|
|
13377
13384
|
});
|
|
@@ -13499,13 +13506,19 @@ var Renderer = class {
|
|
|
13499
13506
|
return this.rootConfig.jsxRenderer || {};
|
|
13500
13507
|
}
|
|
13501
13508
|
/**
|
|
13502
|
-
*
|
|
13503
|
-
* `preact-render-to-string` depending if the
|
|
13504
|
-
* in `root.config.ts`.
|
|
13509
|
+
* Resolves a synchronous JSX render function, using either the
|
|
13510
|
+
* `@blinkk/root/jsx` package or `preact-render-to-string` depending if the
|
|
13511
|
+
* `jsxRenderer` config is set up in `root.config.ts`.
|
|
13512
|
+
*
|
|
13513
|
+
* Resolving the renderer up front (rather than awaiting inside the render
|
|
13514
|
+
* call) allows callers that temporarily swap global state (e.g. the
|
|
13515
|
+
* `preact.options.vnode` nonce hook) to render synchronously without
|
|
13516
|
+
* yielding to the event loop.
|
|
13505
13517
|
*/
|
|
13506
|
-
async
|
|
13518
|
+
async getJsxRenderFn() {
|
|
13507
13519
|
if (this.rootConfig.jsxRenderer?.mode) {
|
|
13508
|
-
|
|
13520
|
+
const options = this.getJsxRenderOptions();
|
|
13521
|
+
return (vnode) => renderJsxToString(vnode, options);
|
|
13509
13522
|
}
|
|
13510
13523
|
const { renderToString } = await import("preact-render-to-string");
|
|
13511
13524
|
if (!renderToString) {
|
|
@@ -13513,7 +13526,16 @@ var Renderer = class {
|
|
|
13513
13526
|
'failed to render jsx. either install preact-render-to-string or add the "jsxRenderer" config to root.config.ts'
|
|
13514
13527
|
);
|
|
13515
13528
|
}
|
|
13516
|
-
return renderToString(vnode);
|
|
13529
|
+
return (vnode) => renderToString(vnode);
|
|
13530
|
+
}
|
|
13531
|
+
/**
|
|
13532
|
+
* Renders JSX via either the `@blinkk/root/jsx` package or
|
|
13533
|
+
* `preact-render-to-string` depending if the `jsxRenderer` config is set up
|
|
13534
|
+
* in `root.config.ts`.
|
|
13535
|
+
*/
|
|
13536
|
+
async renderJsx(vnode) {
|
|
13537
|
+
const render = await this.getJsxRenderFn();
|
|
13538
|
+
return render(vnode);
|
|
13517
13539
|
}
|
|
13518
13540
|
getConfiguredStyleEntries() {
|
|
13519
13541
|
const styleEntries = this.rootConfig.styles?.entries || [];
|
|
@@ -13685,94 +13707,13 @@ ${content}`;
|
|
|
13685
13707
|
);
|
|
13686
13708
|
return { jsDeps, cssDeps };
|
|
13687
13709
|
}
|
|
13688
|
-
/**
|
|
13689
|
-
* Returns the `security` config value with default values inserted wherever
|
|
13690
|
-
* a user config value is blank or set to `true`.
|
|
13691
|
-
*/
|
|
13692
|
-
getSecurityConfig() {
|
|
13693
|
-
const userConfig = this.rootConfig.server?.security || {};
|
|
13694
|
-
const securityConfig = {};
|
|
13695
|
-
if (isTrueOrUndefined(userConfig.contentSecurityPolicy)) {
|
|
13696
|
-
securityConfig.contentSecurityPolicy = {
|
|
13697
|
-
directives: {
|
|
13698
|
-
"base-uri": ["'none'"],
|
|
13699
|
-
"object-src": ["'none'"],
|
|
13700
|
-
// NOTE: nonce is automatically added to this list.
|
|
13701
|
-
"script-src": [
|
|
13702
|
-
"'unsafe-inline'",
|
|
13703
|
-
"'unsafe-eval'",
|
|
13704
|
-
"'strict-dynamic' https: http:"
|
|
13705
|
-
]
|
|
13706
|
-
},
|
|
13707
|
-
reportOnly: true
|
|
13708
|
-
};
|
|
13709
|
-
} else {
|
|
13710
|
-
securityConfig.contentSecurityPolicy = userConfig.contentSecurityPolicy;
|
|
13711
|
-
}
|
|
13712
|
-
if (isTrueOrUndefined(userConfig.xFrameOptions)) {
|
|
13713
|
-
securityConfig.xFrameOptions = "SAMEORIGIN";
|
|
13714
|
-
} else {
|
|
13715
|
-
securityConfig.xFrameOptions = userConfig.xFrameOptions;
|
|
13716
|
-
}
|
|
13717
|
-
securityConfig.strictTransportSecurity = userConfig.strictTransportSecurity ?? true;
|
|
13718
|
-
securityConfig.xContentTypeOptions = userConfig.xContentTypeOptions ?? true;
|
|
13719
|
-
securityConfig.xXssProtection = userConfig.xXssProtection ?? true;
|
|
13720
|
-
return securityConfig;
|
|
13721
|
-
}
|
|
13722
13710
|
/**
|
|
13723
13711
|
* Generates a random string that can be used as the "nonce" value for CSP.
|
|
13724
13712
|
*/
|
|
13725
13713
|
generateNonce() {
|
|
13726
13714
|
return crypto.randomBytes(16).toString("base64");
|
|
13727
13715
|
}
|
|
13728
|
-
/**
|
|
13729
|
-
* Sets security-related HTTP headers.
|
|
13730
|
-
*/
|
|
13731
|
-
setSecurityHeaders(res, options) {
|
|
13732
|
-
const securityConfig = options.securityConfig;
|
|
13733
|
-
const contentSecurityPolicy = securityConfig.contentSecurityPolicy;
|
|
13734
|
-
if (typeof contentSecurityPolicy === "object") {
|
|
13735
|
-
const directives = { ...contentSecurityPolicy.directives };
|
|
13736
|
-
if (options.nonce) {
|
|
13737
|
-
const scriptSrc = directives["script-src"] || [
|
|
13738
|
-
"'unsafe-inline'",
|
|
13739
|
-
"'unsafe-eval'",
|
|
13740
|
-
"'strict-dynamic' https: http:"
|
|
13741
|
-
];
|
|
13742
|
-
const scriptSrcWithNonce = [...scriptSrc, `'nonce-${options.nonce}'`];
|
|
13743
|
-
directives["script-src"] = scriptSrcWithNonce;
|
|
13744
|
-
}
|
|
13745
|
-
const headerSegments = [];
|
|
13746
|
-
Object.entries(directives).forEach(([key, values]) => {
|
|
13747
|
-
headerSegments.push([key, ...values].join(" "));
|
|
13748
|
-
});
|
|
13749
|
-
const csp = headerSegments.join("; ");
|
|
13750
|
-
if (contentSecurityPolicy.reportOnly === false) {
|
|
13751
|
-
res.setHeader("content-security-policy", csp);
|
|
13752
|
-
} else {
|
|
13753
|
-
res.setHeader("content-security-policy-report-only", csp);
|
|
13754
|
-
}
|
|
13755
|
-
}
|
|
13756
|
-
if (typeof securityConfig.xFrameOptions === "string") {
|
|
13757
|
-
res.setHeader("x-frame-options", securityConfig.xFrameOptions);
|
|
13758
|
-
}
|
|
13759
|
-
if (securityConfig.strictTransportSecurity) {
|
|
13760
|
-
res.setHeader(
|
|
13761
|
-
"strict-transport-security",
|
|
13762
|
-
"max-age=63072000; includeSubdomains; preload"
|
|
13763
|
-
);
|
|
13764
|
-
}
|
|
13765
|
-
if (securityConfig.xContentTypeOptions) {
|
|
13766
|
-
res.setHeader("x-content-type-options", "nosniff");
|
|
13767
|
-
}
|
|
13768
|
-
if (securityConfig.xXssProtection) {
|
|
13769
|
-
res.setHeader("x-xss-protection", "1; mode=block");
|
|
13770
|
-
}
|
|
13771
|
-
}
|
|
13772
13716
|
};
|
|
13773
|
-
function isTrueOrUndefined(value) {
|
|
13774
|
-
return value === true || value === void 0;
|
|
13775
|
-
}
|
|
13776
13717
|
function sortLocales(a, b) {
|
|
13777
13718
|
if (a === "x-default") {
|
|
13778
13719
|
return -1;
|