astro 7.0.0-alpha.2 → 7.0.0-beta.4
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/assets/build/generate.js +4 -3
- package/dist/assets/fonts/core/collect-font-data.js +1 -0
- package/dist/assets/fonts/types.d.ts +1 -0
- package/dist/cli/add/index.js +1 -44
- package/dist/cli/dev/background.js +1 -1
- package/dist/cli/dev/index.js +1 -1
- package/dist/cli/flags.js +4 -6
- package/dist/cli/help/index.js +1 -2
- package/dist/cli/index.js +1 -15
- package/dist/cli/infra/build-time-astro-version-provider.js +1 -1
- package/dist/container/index.d.ts +3 -3
- package/dist/container/index.js +1 -4
- package/dist/content/content-layer.js +3 -3
- package/dist/content/runtime.d.ts +1 -1
- package/dist/content/runtime.js +1 -0
- package/dist/content/vite-plugin-content-virtual-mod.js +27 -0
- package/dist/core/app/base.d.ts +1 -1
- package/dist/core/app/base.js +14 -24
- package/dist/core/app/dev/pipeline.js +0 -9
- package/dist/core/app/manifest.d.ts +0 -2
- package/dist/core/app/manifest.js +0 -8
- package/dist/core/app/types.d.ts +1 -8
- package/dist/core/base-pipeline.d.ts +3 -9
- package/dist/core/base-pipeline.js +4 -23
- package/dist/core/build/app.d.ts +0 -2
- package/dist/core/build/app.js +0 -5
- package/dist/core/build/generate.js +0 -14
- package/dist/core/build/pipeline.js +0 -9
- package/dist/core/build/plugins/plugin-css.js +1 -0
- package/dist/core/build/plugins/plugin-manifest.js +4 -9
- package/dist/core/config/config.js +3 -2
- package/dist/core/config/schemas/base.d.ts +9 -22
- package/dist/core/config/schemas/base.js +11 -27
- package/dist/core/config/schemas/relative.d.ts +15 -36
- package/dist/core/config/validate.js +10 -2
- package/dist/core/constants.js +1 -1
- package/dist/core/dev/dev.js +1 -1
- package/dist/core/errors/default-handler.js +21 -8
- package/dist/core/fetch/fetch-state.js +3 -16
- package/dist/core/fetch/types.d.ts +1 -1
- package/dist/core/fetch/vite-plugin.js +4 -6
- package/dist/core/hono/index.d.ts +1 -0
- package/dist/core/hono/index.js +1 -0
- package/dist/core/logger/impls/node.js +0 -1
- package/dist/core/logger/load.js +3 -2
- package/dist/core/messages/runtime.js +1 -1
- package/dist/core/middleware/index.js +8 -1
- package/dist/core/middleware/vite-plugin.d.ts +1 -0
- package/dist/core/middleware/vite-plugin.js +5 -1
- package/dist/core/util/normalized-url.js +2 -5
- package/dist/core/util/pathname.d.ts +13 -7
- package/dist/core/util/pathname.js +9 -6
- package/dist/i18n/index.js +6 -2
- package/dist/manifest/serialized.js +4 -5
- package/dist/runtime/server/index.d.ts +1 -1
- package/dist/runtime/server/index.js +4 -0
- package/dist/runtime/server/jsx.js +2 -1
- package/dist/runtime/server/render/astro/render-template.d.ts +1 -1
- package/dist/runtime/server/render/astro/render.d.ts +0 -4
- package/dist/runtime/server/render/astro/render.js +76 -68
- package/dist/runtime/server/render/head.js +2 -1
- package/dist/runtime/server/render/index.d.ts +1 -0
- package/dist/runtime/server/render/index.js +2 -0
- package/dist/runtime/server/render/page.js +9 -44
- package/dist/runtime/server/render/streaming.d.ts +23 -0
- package/dist/runtime/server/render/streaming.js +238 -0
- package/dist/runtime/server/render/util.js +5 -1
- package/dist/types/public/config.d.ts +115 -123
- package/dist/types/public/context.d.ts +1 -1
- package/dist/types/public/internal.d.ts +0 -15
- package/dist/vite-plugin-app/app.js +1 -1
- package/dist/vite-plugin-app/pipeline.js +0 -9
- package/dist/vite-plugin-hmr-reload/index.js +19 -6
- package/dist/vite-plugin-html/transform/slots.js +4 -1
- package/dist/vite-plugin-pages/pages.d.ts +11 -0
- package/dist/vite-plugin-pages/pages.js +1 -3
- package/package.json +13 -7
- package/dist/cli/db/index.d.ts +0 -4
- package/dist/cli/db/index.js +0 -25
- package/dist/jsx/rehype.d.ts +0 -5
- package/dist/jsx/rehype.js +0 -241
- package/dist/runtime/server/html-string-cache.d.ts +0 -48
- package/dist/runtime/server/html-string-cache.js +0 -119
- package/dist/runtime/server/render/queue/builder.d.ts +0 -14
- package/dist/runtime/server/render/queue/builder.js +0 -182
- package/dist/runtime/server/render/queue/jsx-builder.d.ts +0 -33
- package/dist/runtime/server/render/queue/jsx-builder.js +0 -146
- package/dist/runtime/server/render/queue/pool.d.ts +0 -123
- package/dist/runtime/server/render/queue/pool.js +0 -203
- package/dist/runtime/server/render/queue/renderer.d.ts +0 -12
- package/dist/runtime/server/render/queue/renderer.js +0 -103
- package/dist/runtime/server/render/queue/types.d.ts +0 -81
- package/dist/runtime/server/render/queue/types.js +0 -0
|
@@ -0,0 +1,238 @@
|
|
|
1
|
+
import { isVNode } from "../../../jsx-runtime/index.js";
|
|
2
|
+
import { escapeHTML, HTMLString, isHTMLString, markHTMLString } from "../escape.js";
|
|
3
|
+
import { spreadAttributes } from "../index.js";
|
|
4
|
+
import { isPromise } from "../util.js";
|
|
5
|
+
import { renderJSX } from "../jsx.js";
|
|
6
|
+
import { renderChild } from "./any.js";
|
|
7
|
+
import { Fragment } from "./common.js";
|
|
8
|
+
import { createBufferedRenderer, voidElementNames } from "./util.js";
|
|
9
|
+
import { isAstroComponentFactory } from "./astro/factory.js";
|
|
10
|
+
import { createAstroComponentInstance } from "./astro/instance.js";
|
|
11
|
+
import { isRenderTemplateResult } from "./astro/render-template.js";
|
|
12
|
+
import { containsServerDirective, ServerIslandComponent } from "./server-islands.js";
|
|
13
|
+
const ClientOnlyPlaceholder = "astro-client-only";
|
|
14
|
+
class TemplateFrame {
|
|
15
|
+
/** The RenderTemplateResult this frame walks. */
|
|
16
|
+
templateResult;
|
|
17
|
+
/** Resume position: the next `htmlParts`/`expressions` index to process. */
|
|
18
|
+
cursor;
|
|
19
|
+
constructor(templateResult) {
|
|
20
|
+
this.templateResult = templateResult;
|
|
21
|
+
this.cursor = 0;
|
|
22
|
+
}
|
|
23
|
+
storeCursor(index) {
|
|
24
|
+
this.cursor = index;
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
async function renderStreaming(root, result, destination) {
|
|
28
|
+
const stack = [root];
|
|
29
|
+
const openTagCache = /* @__PURE__ */ new Map();
|
|
30
|
+
const closeTagCache = /* @__PURE__ */ new Map();
|
|
31
|
+
const closeTagFor = (type) => {
|
|
32
|
+
let tag = closeTagCache.get(type);
|
|
33
|
+
if (tag === void 0) {
|
|
34
|
+
tag = new HTMLString(`</${type}>`);
|
|
35
|
+
closeTagCache.set(type, tag);
|
|
36
|
+
}
|
|
37
|
+
return tag;
|
|
38
|
+
};
|
|
39
|
+
let batch = "";
|
|
40
|
+
let buffered = false;
|
|
41
|
+
let firstAsync = null;
|
|
42
|
+
const tail = [];
|
|
43
|
+
let tailStatic = "";
|
|
44
|
+
const emitStatic = (s) => {
|
|
45
|
+
if (!s) return;
|
|
46
|
+
if (buffered) tailStatic += s;
|
|
47
|
+
else batch += s;
|
|
48
|
+
};
|
|
49
|
+
const flushTailStatic = () => {
|
|
50
|
+
if (tailStatic) {
|
|
51
|
+
tail.push(tailStatic);
|
|
52
|
+
tailStatic = "";
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
const renderDynamic = (node) => (d) => {
|
|
56
|
+
if (isVNode(node)) {
|
|
57
|
+
return renderJSX(result, node).then((out) => renderChild(d, out));
|
|
58
|
+
}
|
|
59
|
+
return renderChild(d, node);
|
|
60
|
+
};
|
|
61
|
+
const handleVNode = (vnode) => {
|
|
62
|
+
const type = vnode.type;
|
|
63
|
+
if (!type) {
|
|
64
|
+
throw new Error(
|
|
65
|
+
`Unable to render ${result.pathname} because it contains an undefined Component!
|
|
66
|
+
Did you forget to import the component or is it possible there is a typo?`
|
|
67
|
+
);
|
|
68
|
+
}
|
|
69
|
+
if (type === Fragment) {
|
|
70
|
+
stack.push(vnode.props?.children);
|
|
71
|
+
return;
|
|
72
|
+
}
|
|
73
|
+
if (isAstroComponentFactory(type)) {
|
|
74
|
+
const props = {};
|
|
75
|
+
const slots = {};
|
|
76
|
+
for (const [key, value] of Object.entries(vnode.props ?? {})) {
|
|
77
|
+
if (key === "children" || value && typeof value === "object" && value["$$slot"]) {
|
|
78
|
+
slots[key === "children" ? "default" : key] = () => renderJSX(result, value);
|
|
79
|
+
} else {
|
|
80
|
+
props[key] = value;
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
const displayName = type.name || "Anonymous";
|
|
84
|
+
if (containsServerDirective(props)) {
|
|
85
|
+
const island = new ServerIslandComponent(result, props, slots, displayName);
|
|
86
|
+
result._metadata.propagators.add(island);
|
|
87
|
+
stack.push(island);
|
|
88
|
+
return;
|
|
89
|
+
}
|
|
90
|
+
stack.push(createAstroComponentInstance(result, displayName, type, props, slots));
|
|
91
|
+
return;
|
|
92
|
+
}
|
|
93
|
+
if (typeof type === "string" && type !== ClientOnlyPlaceholder) {
|
|
94
|
+
const props = vnode.props;
|
|
95
|
+
let hasAttrs = false;
|
|
96
|
+
if (props) {
|
|
97
|
+
for (const key in props) {
|
|
98
|
+
if (key !== "children") {
|
|
99
|
+
hasAttrs = true;
|
|
100
|
+
break;
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
const children = props?.children;
|
|
105
|
+
const isVoid = (children == null || children === "") && voidElementNames.test(type);
|
|
106
|
+
if (!hasAttrs) {
|
|
107
|
+
const key = isVoid ? `${type}/` : type;
|
|
108
|
+
let openTag = openTagCache.get(key);
|
|
109
|
+
if (openTag === void 0) {
|
|
110
|
+
openTag = isVoid ? `<${type}/>` : `<${type}>`;
|
|
111
|
+
openTagCache.set(key, openTag);
|
|
112
|
+
}
|
|
113
|
+
emitStatic(openTag);
|
|
114
|
+
if (!isVoid) {
|
|
115
|
+
stack.push(closeTagFor(type));
|
|
116
|
+
}
|
|
117
|
+
} else {
|
|
118
|
+
const { children: _children, ...attrsProps } = props ?? {};
|
|
119
|
+
const attrs = spreadAttributes(attrsProps);
|
|
120
|
+
if (isVoid) {
|
|
121
|
+
emitStatic(`<${type}${attrs}/>`);
|
|
122
|
+
return;
|
|
123
|
+
}
|
|
124
|
+
emitStatic(`<${type}${attrs}>`);
|
|
125
|
+
stack.push(markHTMLString(`</${type}>`));
|
|
126
|
+
}
|
|
127
|
+
if (!isVoid && children != null && children !== "") {
|
|
128
|
+
if (typeof children === "string" && (type === "style" || type === "script")) {
|
|
129
|
+
stack.push(markHTMLString(children));
|
|
130
|
+
} else {
|
|
131
|
+
stack.push(children);
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
return;
|
|
135
|
+
}
|
|
136
|
+
if (typeof type === "function" && vnode.props?.["server:root"]) {
|
|
137
|
+
stack.push(type(vnode.props ?? {}));
|
|
138
|
+
return;
|
|
139
|
+
}
|
|
140
|
+
stack.push(renderJSX(result, vnode));
|
|
141
|
+
};
|
|
142
|
+
while (stack.length > 0) {
|
|
143
|
+
const node = stack.pop();
|
|
144
|
+
if (node == null || node === false) continue;
|
|
145
|
+
if (node instanceof TemplateFrame) {
|
|
146
|
+
const htmlParts = node.templateResult.htmlParts;
|
|
147
|
+
const expressions = node.templateResult.expressions;
|
|
148
|
+
let i = node.cursor;
|
|
149
|
+
while (i < htmlParts.length) {
|
|
150
|
+
if (htmlParts[i]) {
|
|
151
|
+
emitStatic(htmlParts[i]);
|
|
152
|
+
}
|
|
153
|
+
if (i >= expressions.length) {
|
|
154
|
+
break;
|
|
155
|
+
}
|
|
156
|
+
const expression = expressions[i];
|
|
157
|
+
i++;
|
|
158
|
+
if (expression == null || expression === false) continue;
|
|
159
|
+
const expressionType = typeof expression;
|
|
160
|
+
if (expressionType === "string") {
|
|
161
|
+
emitStatic(escapeHTML(expression));
|
|
162
|
+
continue;
|
|
163
|
+
}
|
|
164
|
+
if (expressionType === "number" || expressionType === "bigint" || expressionType === "boolean") {
|
|
165
|
+
emitStatic(String(expression));
|
|
166
|
+
continue;
|
|
167
|
+
}
|
|
168
|
+
if (expression instanceof HTMLString || isHTMLString(expression)) {
|
|
169
|
+
emitStatic(expression.toString());
|
|
170
|
+
continue;
|
|
171
|
+
}
|
|
172
|
+
node.storeCursor(i);
|
|
173
|
+
stack.push(node);
|
|
174
|
+
stack.push(expression);
|
|
175
|
+
break;
|
|
176
|
+
}
|
|
177
|
+
continue;
|
|
178
|
+
}
|
|
179
|
+
const nodeType = typeof node;
|
|
180
|
+
if (nodeType === "string") {
|
|
181
|
+
emitStatic(escapeHTML(node));
|
|
182
|
+
continue;
|
|
183
|
+
}
|
|
184
|
+
if (nodeType === "number" || nodeType === "bigint" || nodeType === "boolean") {
|
|
185
|
+
emitStatic(String(node));
|
|
186
|
+
continue;
|
|
187
|
+
}
|
|
188
|
+
if (node instanceof HTMLString || isHTMLString(node)) {
|
|
189
|
+
emitStatic(node.toString());
|
|
190
|
+
continue;
|
|
191
|
+
}
|
|
192
|
+
if (Array.isArray(node)) {
|
|
193
|
+
for (let i = node.length - 1; i >= 0; i--) stack.push(node[i]);
|
|
194
|
+
continue;
|
|
195
|
+
}
|
|
196
|
+
if (isRenderTemplateResult(node)) {
|
|
197
|
+
stack.push(new TemplateFrame(node));
|
|
198
|
+
continue;
|
|
199
|
+
}
|
|
200
|
+
if (isVNode(node)) {
|
|
201
|
+
handleVNode(node);
|
|
202
|
+
continue;
|
|
203
|
+
}
|
|
204
|
+
if (!buffered) {
|
|
205
|
+
if (batch) {
|
|
206
|
+
destination.write(markHTMLString(batch));
|
|
207
|
+
batch = "";
|
|
208
|
+
}
|
|
209
|
+
const rendered = renderDynamic(node)(destination);
|
|
210
|
+
if (isPromise(rendered)) {
|
|
211
|
+
buffered = true;
|
|
212
|
+
firstAsync = rendered;
|
|
213
|
+
}
|
|
214
|
+
} else {
|
|
215
|
+
flushTailStatic();
|
|
216
|
+
tail.push(createBufferedRenderer(destination, renderDynamic(node)));
|
|
217
|
+
}
|
|
218
|
+
}
|
|
219
|
+
if (!buffered) {
|
|
220
|
+
if (batch) {
|
|
221
|
+
destination.write(markHTMLString(batch));
|
|
222
|
+
}
|
|
223
|
+
return;
|
|
224
|
+
}
|
|
225
|
+
await firstAsync;
|
|
226
|
+
flushTailStatic();
|
|
227
|
+
for (const seg of tail) {
|
|
228
|
+
if (typeof seg === "string") {
|
|
229
|
+
destination.write(markHTMLString(seg));
|
|
230
|
+
} else {
|
|
231
|
+
const r = seg.flush();
|
|
232
|
+
if (isPromise(r)) await r;
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
export {
|
|
237
|
+
renderStreaming
|
|
238
|
+
};
|
|
@@ -6,6 +6,7 @@ const htmlBooleanAttributes = /^(?:allowfullscreen|async|autofocus|autoplay|chec
|
|
|
6
6
|
const AMPERSAND_REGEX = /&/g;
|
|
7
7
|
const DOUBLE_QUOTE_REGEX = /"/g;
|
|
8
8
|
const STATIC_DIRECTIVES = /* @__PURE__ */ new Set(["set:html", "set:text"]);
|
|
9
|
+
const INVALID_ATTR_NAME_CHAR = /[\s"'>/=]/;
|
|
9
10
|
const toIdent = (k) => k.trim().replace(/(?!^)\b\w|\s+|\W+/g, (match, index) => {
|
|
10
11
|
if (/\W/.test(match)) return "";
|
|
11
12
|
return index === 0 ? match : match.toUpperCase();
|
|
@@ -43,6 +44,9 @@ function addAttribute(value, key, shouldEscape = true, tagName = "") {
|
|
|
43
44
|
if (value == null) {
|
|
44
45
|
return "";
|
|
45
46
|
}
|
|
47
|
+
if (INVALID_ATTR_NAME_CHAR.test(key)) {
|
|
48
|
+
return "";
|
|
49
|
+
}
|
|
46
50
|
if (STATIC_DIRECTIVES.has(key)) {
|
|
47
51
|
console.warn(`[astro] The "${key}" directive cannot be applied dynamically at runtime. It will not be rendered as an attribute.
|
|
48
52
|
|
|
@@ -149,7 +153,7 @@ class BufferedRenderer {
|
|
|
149
153
|
function createBufferedRenderer(destination, renderFunction) {
|
|
150
154
|
return new BufferedRenderer(destination, renderFunction);
|
|
151
155
|
}
|
|
152
|
-
const isNode = typeof process !== "undefined" && Object.prototype.toString.call(process) === "[object process]"
|
|
156
|
+
const isNode = typeof process !== "undefined" && Object.prototype.toString.call(process) === "[object process]";
|
|
153
157
|
const isDeno = typeof Deno !== "undefined";
|
|
154
158
|
function promiseWithResolvers() {
|
|
155
159
|
let resolve, reject;
|
|
@@ -1321,6 +1321,103 @@ export interface AstroUserConfig<TLocales extends Locales = never, TDriver exten
|
|
|
1321
1321
|
server?: ServerConfig | ((options: {
|
|
1322
1322
|
command: 'dev' | 'preview';
|
|
1323
1323
|
}) => ServerConfig);
|
|
1324
|
+
/**
|
|
1325
|
+
* @docs
|
|
1326
|
+
* @kind heading
|
|
1327
|
+
* @name fetchFile
|
|
1328
|
+
* @type {string | null}
|
|
1329
|
+
* @default `'fetch'`
|
|
1330
|
+
* @version 7.0.0
|
|
1331
|
+
* @description
|
|
1332
|
+
*
|
|
1333
|
+
* Customizes the file used as the fetch entrypoint inside `srcDir`.
|
|
1334
|
+
* Defaults to `'fetch'`, meaning Astro looks for `src/fetch.ts` (or `.js` / `.mjs` / `.mts`).
|
|
1335
|
+
*
|
|
1336
|
+
* The fetch file allows you to compose Astro's request pipeline with the
|
|
1337
|
+
* Web Fetch standard or your own Hono middleware.
|
|
1338
|
+
*
|
|
1339
|
+
* If you already have a `src/fetch.ts` file in use for other purposes, define a
|
|
1340
|
+
* different filename or set the value to `null` to disable the entrypoint:
|
|
1341
|
+
*
|
|
1342
|
+
* ```js
|
|
1343
|
+
* // astro.config.mjs
|
|
1344
|
+
* import { defineConfig } from 'astro/config';
|
|
1345
|
+
*
|
|
1346
|
+
* export default defineConfig({
|
|
1347
|
+
* fetchFile: 'handler',
|
|
1348
|
+
* });
|
|
1349
|
+
* ```
|
|
1350
|
+
*
|
|
1351
|
+
* Learn more about customizing the request pipeline in the [advanced routing guide](https://v7.docs.astro.build/en/guides/routing/#advanced-routing).
|
|
1352
|
+
*/
|
|
1353
|
+
fetchFile?: string | null;
|
|
1354
|
+
/**
|
|
1355
|
+
* @docs
|
|
1356
|
+
* @kind heading
|
|
1357
|
+
* @name Logger Options
|
|
1358
|
+
* @type {LoggerHandlerConfig}
|
|
1359
|
+
* @default `undefined`
|
|
1360
|
+
* @version 7.0.0
|
|
1361
|
+
* @description
|
|
1362
|
+
*
|
|
1363
|
+
* Configures how Astro logs messages during development and production.
|
|
1364
|
+
*
|
|
1365
|
+
* By default, Astro uses a built-in logger that outputs human-friendly logs to the console. You can customize this behavior by providing [your own logger handler](https://v7.docs.astro.build/en/reference/logger-reference/#custom-loggers) or by using one of the [built-in log handlers](https://v7.docs.astro.build/en/reference/logger-reference/#built-in-loggers):
|
|
1366
|
+
*
|
|
1367
|
+
* ```js
|
|
1368
|
+
* // astro.config.mjs
|
|
1369
|
+
* import { defineConfig, logHandlers } from 'astro/config';
|
|
1370
|
+
*
|
|
1371
|
+
* export default defineConfig({
|
|
1372
|
+
* logger: logHandlers.json({ level: 'info' })
|
|
1373
|
+
* });
|
|
1374
|
+
* ```
|
|
1375
|
+
*
|
|
1376
|
+
* See [the logger API reference](https://v7.docs.astro.build/en/reference/logger-reference/) for more information.
|
|
1377
|
+
*/
|
|
1378
|
+
logger?: LoggerHandlerConfig;
|
|
1379
|
+
/**
|
|
1380
|
+
* @docs
|
|
1381
|
+
* @name logger.entrypoint
|
|
1382
|
+
* @type {string}
|
|
1383
|
+
* @version 7.0.0
|
|
1384
|
+
* @description
|
|
1385
|
+
*
|
|
1386
|
+
* The entrypoint of the log handler. This can be a path to a file in your project or an npm package:
|
|
1387
|
+
*
|
|
1388
|
+
* ```js title="astro.config.mjs"
|
|
1389
|
+
* import { defineConfig } from 'astro/config';
|
|
1390
|
+
*
|
|
1391
|
+
* export default defineConfig({
|
|
1392
|
+
* logger: {
|
|
1393
|
+
* entrypoint: "@org/astro-logger",
|
|
1394
|
+
* }
|
|
1395
|
+
* });
|
|
1396
|
+
* ```
|
|
1397
|
+
*/
|
|
1398
|
+
/**
|
|
1399
|
+
* @docs
|
|
1400
|
+
* @name logger.config
|
|
1401
|
+
* @type {Record<string, unknown> | undefined}
|
|
1402
|
+
* @version 7.0.0
|
|
1403
|
+
* @default `{}`
|
|
1404
|
+
* @description
|
|
1405
|
+
*
|
|
1406
|
+
* The configuration object for the log handler. The options depend on the configured logger.
|
|
1407
|
+
*
|
|
1408
|
+
* ```js title="astro.config.mjs"
|
|
1409
|
+
* import { defineConfig } from 'astro/config';
|
|
1410
|
+
*
|
|
1411
|
+
* export default defineConfig({
|
|
1412
|
+
* logger: {
|
|
1413
|
+
* entrypoint: "@org/astro-logger",
|
|
1414
|
+
* config: {
|
|
1415
|
+
* level: "error"
|
|
1416
|
+
* }
|
|
1417
|
+
* }
|
|
1418
|
+
* });
|
|
1419
|
+
* ```
|
|
1420
|
+
*/
|
|
1324
1421
|
/**
|
|
1325
1422
|
* @docs
|
|
1326
1423
|
* @kind heading
|
|
@@ -2071,8 +2168,24 @@ export interface AstroUserConfig<TLocales extends Locales = never, TDriver exten
|
|
|
2071
2168
|
* @type {MarkdownProcessor}
|
|
2072
2169
|
* @version 6.4.0
|
|
2073
2170
|
* @description
|
|
2074
|
-
* Configures the Markdown processor used to render `.md` files. Defaults to `
|
|
2075
|
-
* `@astrojs/markdown-
|
|
2171
|
+
* Configures the Markdown processor used to render `.md` files. Defaults to `satteri()` from
|
|
2172
|
+
* `@astrojs/markdown-satteri`, Astro's native Markdown pipeline.
|
|
2173
|
+
*
|
|
2174
|
+
* ```js
|
|
2175
|
+
* // astro.config.mjs
|
|
2176
|
+
* import { defineConfig } from 'astro/config';
|
|
2177
|
+
* import { satteri } from '@astrojs/markdown-satteri';
|
|
2178
|
+
*
|
|
2179
|
+
* export default defineConfig({
|
|
2180
|
+
* markdown: {
|
|
2181
|
+
* processor: satteri({
|
|
2182
|
+
* features: { gfm: false },
|
|
2183
|
+
* }),
|
|
2184
|
+
* },
|
|
2185
|
+
* });
|
|
2186
|
+
* ```
|
|
2187
|
+
*
|
|
2188
|
+
* To keep the remark/rehype pipeline, install `@astrojs/markdown-remark` and pass `unified()`:
|
|
2076
2189
|
*
|
|
2077
2190
|
* ```js
|
|
2078
2191
|
* // astro.config.mjs
|
|
@@ -2676,40 +2789,6 @@ export interface AstroUserConfig<TLocales extends Locales = never, TDriver exten
|
|
|
2676
2789
|
* These flags are not guaranteed to be stable.
|
|
2677
2790
|
*/
|
|
2678
2791
|
experimental?: {
|
|
2679
|
-
/**
|
|
2680
|
-
* @name experimental.advancedRouting
|
|
2681
|
-
* @type {boolean | object}
|
|
2682
|
-
* @default `false`
|
|
2683
|
-
* @description
|
|
2684
|
-
* Enables `src/app.ts` as an advanced routing entrypoint, allowing you to
|
|
2685
|
-
* compose Astro's request pipeline with the Web Fetch standard or your own Hono middleware.
|
|
2686
|
-
*
|
|
2687
|
-
* Pass `true` to enable with default settings, or an object to customize:
|
|
2688
|
-
*
|
|
2689
|
-
* ```js
|
|
2690
|
-
* export default defineConfig({
|
|
2691
|
-
* experimental: {
|
|
2692
|
-
* advancedRouting: {
|
|
2693
|
-
* fetchFile: 'fetch.ts',
|
|
2694
|
-
* },
|
|
2695
|
-
* },
|
|
2696
|
-
* });
|
|
2697
|
-
* ```
|
|
2698
|
-
*/
|
|
2699
|
-
advancedRouting?: boolean | {
|
|
2700
|
-
/**
|
|
2701
|
-
* @name experimental.advancedRouting.fetchFile
|
|
2702
|
-
* @type {string | null}
|
|
2703
|
-
* @default 'app'
|
|
2704
|
-
* @description
|
|
2705
|
-
*
|
|
2706
|
-
* Customizes the file used as the advanced routing entrypoint inside `srcDir`.
|
|
2707
|
-
* Defaults to `'app'`, meaning Astro looks for `src/app.ts`.
|
|
2708
|
-
*
|
|
2709
|
-
* If you already have a `src/app.ts` file in use for other purposes, define a different filename or set the value to `null` to disable the entrypoint.
|
|
2710
|
-
*/
|
|
2711
|
-
fetchFile?: string | null;
|
|
2712
|
-
};
|
|
2713
2792
|
/**
|
|
2714
2793
|
*
|
|
2715
2794
|
* @name experimental.clientPrerender
|
|
@@ -2893,93 +2972,6 @@ export interface AstroUserConfig<TLocales extends Locales = never, TDriver exten
|
|
|
2893
2972
|
* ```
|
|
2894
2973
|
*/
|
|
2895
2974
|
routeRules?: RouteRules;
|
|
2896
|
-
/**
|
|
2897
|
-
* @name experimental.queuedRendering
|
|
2898
|
-
* @type {boolean | { poolSize?: number; cache?: boolean }}
|
|
2899
|
-
* @default `false`
|
|
2900
|
-
* @version 6.0.0
|
|
2901
|
-
* @description
|
|
2902
|
-
* Enable queue-based rendering engine instead of the default recursive rendering.
|
|
2903
|
-
*
|
|
2904
|
-
* This new rendering engine comes with a different set of features that you can tweak based on your needs.
|
|
2905
|
-
*
|
|
2906
|
-
* ```js
|
|
2907
|
-
* {
|
|
2908
|
-
* experimental: {
|
|
2909
|
-
* queuedRendering: {
|
|
2910
|
-
* enabled: true
|
|
2911
|
-
* }
|
|
2912
|
-
* }
|
|
2913
|
-
* }
|
|
2914
|
-
* ```
|
|
2915
|
-
*
|
|
2916
|
-
* You can optionally configure the object pool size and HTMLString caching:
|
|
2917
|
-
*
|
|
2918
|
-
* ```js
|
|
2919
|
-
* {
|
|
2920
|
-
* experimental: {
|
|
2921
|
-
* queuedRendering: {
|
|
2922
|
-
* enabled: true,
|
|
2923
|
-
* poolSize: 1000, // default: 1000 for static builds, 0 for SSR
|
|
2924
|
-
* cache: false // default: false (caching can hurt performance)
|
|
2925
|
-
* }
|
|
2926
|
-
* }
|
|
2927
|
-
* }
|
|
2928
|
-
* ```
|
|
2929
|
-
*/
|
|
2930
|
-
queuedRendering?: {
|
|
2931
|
-
/**
|
|
2932
|
-
* @default `false`
|
|
2933
|
-
* @version 6.0.0
|
|
2934
|
-
* @description
|
|
2935
|
-
* Enables the queue-based rendering.
|
|
2936
|
-
*/
|
|
2937
|
-
enabled: boolean;
|
|
2938
|
-
/**
|
|
2939
|
-
* @default 1000
|
|
2940
|
-
* @version 6.0.0
|
|
2941
|
-
* @description
|
|
2942
|
-
* Allows to change how many nodes should be saved in the pool. If 0 is provided, the pool is disabled.
|
|
2943
|
-
* The pool is disabled for dynamic pages, because server requests don't share the same memory.
|
|
2944
|
-
*/
|
|
2945
|
-
poolSize?: number;
|
|
2946
|
-
/**
|
|
2947
|
-
* @default `false`
|
|
2948
|
-
* @version 6.0.0
|
|
2949
|
-
* @description
|
|
2950
|
-
* Enables HTMLString caching to deduplicate repeated HTML fragments during rendering.
|
|
2951
|
-
* When enabled, identical HTML strings (e.g., repeated `<li>` tags) share a single
|
|
2952
|
-
* `HTMLString` object instead of creating a new wrapper per occurrence.
|
|
2953
|
-
* This caching is disabled for dynamic pages.
|
|
2954
|
-
*/
|
|
2955
|
-
contentCache?: boolean;
|
|
2956
|
-
};
|
|
2957
|
-
/**
|
|
2958
|
-
* @name experimental.logger
|
|
2959
|
-
* @type {{ entrypoint: string; config?: Record<string, unknown> }}
|
|
2960
|
-
* @default `undefined`
|
|
2961
|
-
* @version 6.2.0
|
|
2962
|
-
* @description
|
|
2963
|
-
*
|
|
2964
|
-
* Configure a custom logger by defining its entrypoint and, optionally, providing a serializable configuration:
|
|
2965
|
-
*
|
|
2966
|
-
* ```js
|
|
2967
|
-
* // astro.config.mjs
|
|
2968
|
-
* import { defineConfig } from 'astro/config';
|
|
2969
|
-
*
|
|
2970
|
-
* export default defineConfig({
|
|
2971
|
-
* experimental: {
|
|
2972
|
-
* logger: {
|
|
2973
|
-
* entrypoint: "@org/astro-logger",
|
|
2974
|
-
* config: {
|
|
2975
|
-
* level: "error"
|
|
2976
|
-
* }
|
|
2977
|
-
* }
|
|
2978
|
-
* }
|
|
2979
|
-
* });
|
|
2980
|
-
* ```
|
|
2981
|
-
*/
|
|
2982
|
-
logger?: LoggerHandlerConfig;
|
|
2983
2975
|
};
|
|
2984
2976
|
}
|
|
2985
2977
|
/**
|
|
@@ -546,7 +546,7 @@ export interface APIContext<Props extends Record<string, any> = Record<string, a
|
|
|
546
546
|
* Logs a message with `error` level.
|
|
547
547
|
*/
|
|
548
548
|
error: (msg: string) => void;
|
|
549
|
-
}
|
|
549
|
+
};
|
|
550
550
|
/**
|
|
551
551
|
* The route currently rendered. It's stripped of the `srcDir` and the `pages` folder, and it doesn't contain the extension.
|
|
552
552
|
*
|
|
@@ -6,8 +6,6 @@ import type { Params } from './common.js';
|
|
|
6
6
|
import type { AstroConfig, RedirectConfig } from './config.js';
|
|
7
7
|
import type { AstroGlobal } from './context.js';
|
|
8
8
|
import type { AstroRenderer } from './integrations.js';
|
|
9
|
-
import type { NodePool } from '../../runtime/server/render/queue/pool.js';
|
|
10
|
-
import type { HTMLStringCache } from '../../runtime/server/html-string-cache.js';
|
|
11
9
|
export type { SSRActions, SSRManifest, SSRManifestCSP } from '../../core/app/types.js';
|
|
12
10
|
export interface NamedSSRLoadedRendererValue extends SSRLoadedRendererValue {
|
|
13
11
|
name: string;
|
|
@@ -233,19 +231,6 @@ export interface SSRResult {
|
|
|
233
231
|
directives: SSRManifestCSP['directives'];
|
|
234
232
|
isStrictDynamic: SSRManifestCSP['isStrictDynamic'];
|
|
235
233
|
internalFetchHeaders?: Record<string, string>;
|
|
236
|
-
/**
|
|
237
|
-
* Experimental: Configuration for queue-based rendering.
|
|
238
|
-
* - enabled: Whether to use queue-based rendering (default: true if config is object)
|
|
239
|
-
* - poolSize: Maximum number of nodes to keep in the object pool (default: 1000, 0 to disable)
|
|
240
|
-
* - cache: Whether to enable HTMLString caching (default: true)
|
|
241
|
-
*/
|
|
242
|
-
_experimentalQueuedRendering?: {
|
|
243
|
-
pool?: NodePool;
|
|
244
|
-
htmlStringCache?: HTMLStringCache;
|
|
245
|
-
enabled?: boolean;
|
|
246
|
-
poolSize?: number;
|
|
247
|
-
contentCache?: boolean;
|
|
248
|
-
};
|
|
249
234
|
}
|
|
250
235
|
/**
|
|
251
236
|
* A hint on whether the Astro runtime needs to wait on a component to render head
|
|
@@ -23,7 +23,7 @@ class AstroServerApp extends BaseApp {
|
|
|
23
23
|
this.manifestData = manifestData;
|
|
24
24
|
}
|
|
25
25
|
/**
|
|
26
|
-
* Loads the user's `src/
|
|
26
|
+
* Loads the user's `src/fetch.ts` (via `virtual:astro:fetchable`) and
|
|
27
27
|
* sets it as the fetch handler. Called on every request so that HMR
|
|
28
28
|
* invalidation of the virtual module is picked up automatically.
|
|
29
29
|
* Vite caches the module internally so repeated calls are cheap.
|
|
@@ -11,9 +11,6 @@ import { isPage } from "../core/util.js";
|
|
|
11
11
|
import { getComponentMetadata } from "../vite-plugin-astro-server/metadata.js";
|
|
12
12
|
import { createResolve } from "../vite-plugin-astro-server/resolve.js";
|
|
13
13
|
import { PAGE_SCRIPT_ID } from "../vite-plugin-scripts/index.js";
|
|
14
|
-
import { newNodePool } from "../runtime/server/render/queue/pool.js";
|
|
15
|
-
import { HTMLStringCache } from "../runtime/server/html-string-cache.js";
|
|
16
|
-
import { queueRenderingEnabled } from "../core/app/manifest.js";
|
|
17
14
|
class RunnablePipeline extends Pipeline {
|
|
18
15
|
getName() {
|
|
19
16
|
return "RunnablePipeline";
|
|
@@ -58,12 +55,6 @@ class RunnablePipeline extends Pipeline {
|
|
|
58
55
|
}) {
|
|
59
56
|
const pipeline = new RunnablePipeline(loader, logger, manifest, settings, getDebugInfo);
|
|
60
57
|
pipeline.routesList = manifestData;
|
|
61
|
-
if (queueRenderingEnabled(manifest.experimentalQueuedRendering)) {
|
|
62
|
-
pipeline.nodePool = newNodePool(manifest.experimentalQueuedRendering);
|
|
63
|
-
if (manifest.experimentalQueuedRendering.contentCache) {
|
|
64
|
-
pipeline.htmlStringCache = new HTMLStringCache(1e3);
|
|
65
|
-
}
|
|
66
|
-
}
|
|
67
58
|
return pipeline;
|
|
68
59
|
}
|
|
69
60
|
async headElements(routeData) {
|
|
@@ -1,15 +1,17 @@
|
|
|
1
1
|
import { isRunnableDevEnvironment } from "vite";
|
|
2
2
|
import { VIRTUAL_PAGE_RESOLVED_MODULE_ID } from "../vite-plugin-pages/const.js";
|
|
3
|
+
import { RESOLVED_MODULE_DEV_CSS_PREFIX } from "../vite-plugin-css/const.js";
|
|
3
4
|
import { getDevCssModuleNameFromPageVirtualModuleName } from "../vite-plugin-css/util.js";
|
|
4
5
|
import { isAstroServerEnvironment } from "../environments.js";
|
|
5
6
|
const STYLE_EXT_REGEX = /\.(?:css|scss|sass|less|styl|pcss)$/i;
|
|
7
|
+
const RAW_QUERY_REGEX = /(?:\?|&)raw(?:&|$)/;
|
|
8
|
+
function hasStyleExtension(id) {
|
|
9
|
+
return STYLE_EXT_REGEX.test(id.split("?")[0]);
|
|
10
|
+
}
|
|
6
11
|
function isStyleModule(mod) {
|
|
7
|
-
if (mod.
|
|
8
|
-
if (mod.
|
|
9
|
-
|
|
10
|
-
if (STYLE_EXT_REGEX.test(idPath)) return true;
|
|
11
|
-
}
|
|
12
|
-
return false;
|
|
12
|
+
if (mod.id && RAW_QUERY_REGEX.test(mod.id) && hasStyleExtension(mod.id)) return false;
|
|
13
|
+
if (mod.file && hasStyleExtension(mod.file)) return true;
|
|
14
|
+
return mod.id ? hasStyleExtension(mod.id) : false;
|
|
13
15
|
}
|
|
14
16
|
function hmrReload() {
|
|
15
17
|
return {
|
|
@@ -65,6 +67,17 @@ function hmrReload() {
|
|
|
65
67
|
return [];
|
|
66
68
|
}
|
|
67
69
|
if (hasSkippedStyleModules) {
|
|
70
|
+
for (const [id, mod] of this.environment.moduleGraph.idToModuleMap) {
|
|
71
|
+
if (id.startsWith(RESOLVED_MODULE_DEV_CSS_PREFIX)) {
|
|
72
|
+
this.environment.moduleGraph.invalidateModule(mod, void 0, timestamp, true);
|
|
73
|
+
if (isRunnableDevEnvironment(this.environment)) {
|
|
74
|
+
const runnerMod = this.environment.runner.evaluatedModules.getModuleById(id);
|
|
75
|
+
if (runnerMod) {
|
|
76
|
+
this.environment.runner.evaluatedModules.invalidateModule(runnerMod);
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
}
|
|
68
81
|
return [];
|
|
69
82
|
}
|
|
70
83
|
if (modules.length > 0) {
|
|
@@ -10,7 +10,10 @@ const rehypeSlots = ({ s }) => {
|
|
|
10
10
|
const end = node.position?.end.offset ?? 0;
|
|
11
11
|
const first = node.children.at(0) ?? node;
|
|
12
12
|
const last = node.children.at(-1) ?? node;
|
|
13
|
-
const text = file.value.slice(
|
|
13
|
+
const text = file.value.slice(
|
|
14
|
+
first.position?.start.offset ?? 0,
|
|
15
|
+
last.position?.end.offset ?? 0
|
|
16
|
+
).toString();
|
|
14
17
|
s.overwrite(
|
|
15
18
|
start,
|
|
16
19
|
end,
|
|
@@ -1,8 +1,19 @@
|
|
|
1
1
|
import type { Plugin as VitePlugin } from 'vite';
|
|
2
2
|
import type { RoutesList } from '../types/astro.js';
|
|
3
|
+
import type { RouteData } from '../types/public/internal.js';
|
|
3
4
|
export declare const VIRTUAL_PAGES_MODULE_ID = "virtual:astro:pages";
|
|
4
5
|
interface PagesPluginOptions {
|
|
5
6
|
routesList: RoutesList;
|
|
6
7
|
}
|
|
8
|
+
/**
|
|
9
|
+
* Filters routes for a specific build environment.
|
|
10
|
+
*
|
|
11
|
+
* Redirect target routes do not need special handling here: they already
|
|
12
|
+
* appear in the routes list with their own `prerender` flag and are
|
|
13
|
+
* included when it matches `isPrerender`. At SSR runtime, redirect
|
|
14
|
+
* responses are generated from route metadata alone (no component is
|
|
15
|
+
* loaded), so the target's component is never needed in the SSR page map.
|
|
16
|
+
*/
|
|
17
|
+
export declare function getRoutesForEnvironment(routes: RouteData[], isPrerender: boolean): Set<RouteData>;
|
|
7
18
|
export declare function pluginPages({ routesList }: PagesPluginOptions): VitePlugin;
|
|
8
19
|
export {};
|