astro 7.2.10 → 7.3.0

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.
Files changed (73) hide show
  1. package/dist/assets/build/generate.d.ts +1 -1
  2. package/dist/assets/build/generate.js +3 -1
  3. package/dist/assets/endpoint/dev.js +6 -5
  4. package/dist/assets/endpoint/generic.js +5 -4
  5. package/dist/assets/endpoint/node.js +3 -3
  6. package/dist/assets/endpoint/shared.d.ts +3 -1
  7. package/dist/assets/endpoint/shared.js +9 -3
  8. package/dist/assets/fonts/config.d.ts +2 -2
  9. package/dist/assets/internal.d.ts +2 -1
  10. package/dist/assets/internal.js +11 -10
  11. package/dist/assets/services/service.d.ts +8 -7
  12. package/dist/assets/services/sharp.js +5 -5
  13. package/dist/assets/vite-plugin-assets.js +22 -5
  14. package/dist/cli/add/index.js +3 -1
  15. package/dist/cli/index.js +1 -1
  16. package/dist/cli/infra/build-time-astro-version-provider.js +1 -1
  17. package/dist/cli/preferences/index.js +32 -30
  18. package/dist/cli/preview/index.js +44 -1
  19. package/dist/cli/telemetry/index.d.ts +2 -1
  20. package/dist/cli/telemetry/index.js +2 -2
  21. package/dist/content/content-layer.js +3 -3
  22. package/dist/content/mutable-data-store.d.ts +2 -1
  23. package/dist/content/mutable-data-store.js +4 -4
  24. package/dist/content/runtime.d.ts +8 -3
  25. package/dist/content/runtime.js +40 -31
  26. package/dist/content/types-generator.js +2 -1
  27. package/dist/content/utils.d.ts +5 -35
  28. package/dist/content/utils.js +71 -65
  29. package/dist/content/vite-plugin-content-imports.js +2 -1
  30. package/dist/core/app/entrypoints/index.d.ts +4 -2
  31. package/dist/core/app/entrypoints/index.js +13 -11
  32. package/dist/core/app/prerender.d.ts +32 -0
  33. package/dist/core/app/prerender.js +22 -0
  34. package/dist/core/build/default-prerenderer.js +5 -2
  35. package/dist/core/build/generate.d.ts +3 -1
  36. package/dist/core/build/generate.js +21 -37
  37. package/dist/core/cache/handler.js +12 -1
  38. package/dist/core/cache/memory-provider.js +35 -8
  39. package/dist/core/cache/types.d.ts +2 -0
  40. package/dist/core/config/schemas/base.d.ts +5 -5
  41. package/dist/core/config/schemas/relative.d.ts +7 -7
  42. package/dist/core/constants.js +1 -1
  43. package/dist/core/cookies/cookies.d.ts +2 -1
  44. package/dist/core/cookies/cookies.js +5 -4
  45. package/dist/core/dev/dev.js +2 -2
  46. package/dist/core/fetch/fetch-state.d.ts +1 -1
  47. package/dist/core/fetch/fetch-state.js +4 -23
  48. package/dist/core/logger/core.d.ts +2 -0
  49. package/dist/core/logger/core.js +14 -0
  50. package/dist/core/logger/vite-plugin.d.ts +13 -2
  51. package/dist/core/logger/vite-plugin.js +8 -7
  52. package/dist/core/messages/runtime.js +1 -1
  53. package/dist/core/middleware/index.js +14 -1
  54. package/dist/core/render-scope/collect.d.ts +24 -0
  55. package/dist/core/render-scope/collect.js +27 -0
  56. package/dist/core/render-scope/node-scope.d.ts +10 -0
  57. package/dist/core/render-scope/node-scope.js +8 -0
  58. package/dist/core/render-scope/record.d.ts +14 -0
  59. package/dist/core/render-scope/record.js +12 -0
  60. package/dist/core/render-scope/scope.d.ts +38 -0
  61. package/dist/core/render-scope/scope.js +28 -0
  62. package/dist/core/rewrites/handler.js +1 -1
  63. package/dist/core/routing/create-manifest.js +5 -1
  64. package/dist/core/server-islands/endpoint.js +4 -1
  65. package/dist/core/sync/index.js +1 -1
  66. package/dist/types/public/integrations.d.ts +20 -13
  67. package/dist/vite-plugin-routes/index.js +22 -8
  68. package/package.json +2 -2
  69. package/templates/content/module.mjs +13 -5
  70. package/dist/core/build/incremental-content-collector.d.ts +0 -10
  71. package/dist/core/build/incremental-content-collector.js +0 -33
  72. package/dist/core/build/incremental-image-collector.d.ts +0 -11
  73. package/dist/core/build/incremental-image-collector.js +0 -32
@@ -12,27 +12,29 @@ import {
12
12
  serializeRouteInfo
13
13
  } from "../manifest.js";
14
14
  import {
15
- beginContentEntryCollection,
16
- endContentEntryCollection
17
- } from "../../build/incremental-content-collector.js";
15
+ getInstalledRenderScope,
16
+ installRenderScope
17
+ } from "../../render-scope/scope.js";
18
+ import { recordStaticImage } from "../../render-scope/record.js";
18
19
  import {
19
- beginImageCollection,
20
- endImageCollection,
21
- recordStaticImage
22
- } from "../../build/incremental-image-collector.js";
20
+ collectPrerenderMetadata
21
+ } from "../../render-scope/collect.js";
22
+ import {
23
+ renderForPrerender
24
+ } from "../prerender.js";
23
25
  export {
24
26
  App,
25
27
  BaseApp,
26
- beginContentEntryCollection,
27
- beginImageCollection,
28
+ collectPrerenderMetadata,
28
29
  createConsoleLogger,
29
30
  deserializeManifest,
30
31
  deserializeRouteData,
31
32
  deserializeRouteInfo,
32
- endContentEntryCollection,
33
- endImageCollection,
34
33
  fromRoutingStrategy,
34
+ getInstalledRenderScope,
35
+ installRenderScope,
35
36
  recordStaticImage,
37
+ renderForPrerender,
36
38
  serializeRouteData,
37
39
  serializeRouteInfo,
38
40
  toRoutingStrategy
@@ -0,0 +1,32 @@
1
+ import type { PrerenderResult } from '../../types/public/integrations.js';
2
+ import type { RouteData } from '../../types/public/internal.js';
3
+ import type { AstroLogger } from '../logger/core.js';
4
+ export interface PrerenderableApp {
5
+ logger: AstroLogger;
6
+ render(request: Request, opts: {
7
+ routeData?: RouteData;
8
+ }): Promise<Response>;
9
+ }
10
+ export interface PrerenderRenderOptions {
11
+ routeData?: RouteData;
12
+ /** Collect per-render incremental metadata and return it on the result. Default false. */
13
+ collectMetadata?: boolean;
14
+ }
15
+ /**
16
+ * Renders a single prerendered path through `app.render`, optionally collecting
17
+ * the per-render incremental metadata (content entries rendered, image
18
+ * transforms resolved) and returning it by value on the result.
19
+ *
20
+ * When not collecting, this short-circuits to a bare `app.render` — the
21
+ * response is the app's own, unbuffered. When collecting, the response body is
22
+ * fully buffered *inside* the render scope so lazily-driven rendering work
23
+ * records before the metadata snapshot; the returned response is a
24
+ * reconstruction carrying the buffered body with status/statusText/headers and
25
+ * body-nullness preserved.
26
+ *
27
+ * This function performs no scope installation; installing a render scope for
28
+ * the rendering runtime is the caller's responsibility. When collection is
29
+ * requested but no scope is installed, `metadata` is `undefined`
30
+ * ("not tracked").
31
+ */
32
+ export declare function renderForPrerender(app: PrerenderableApp, request: Request, options?: PrerenderRenderOptions): Promise<PrerenderResult>;
@@ -0,0 +1,22 @@
1
+ import { collectPrerenderMetadata } from "../render-scope/collect.js";
2
+ const NULL_BODY_STATUSES = [101, 204, 205, 304];
3
+ async function renderForPrerender(app, request, options) {
4
+ const routeData = options?.routeData;
5
+ if (!options?.collectMetadata) {
6
+ return { response: await app.render(request, { routeData }) };
7
+ }
8
+ const { value: response, metadata } = await collectPrerenderMetadata(async () => {
9
+ const rendered = await app.render(request, { routeData });
10
+ const bytes = rendered.body === null ? null : await rendered.arrayBuffer();
11
+ const nullBody = bytes === null || NULL_BODY_STATUSES.includes(rendered.status);
12
+ return new Response(nullBody ? null : bytes, {
13
+ status: rendered.status,
14
+ statusText: rendered.statusText,
15
+ headers: rendered.headers
16
+ });
17
+ }, app.logger);
18
+ return { response, metadata };
19
+ }
20
+ export {
21
+ renderForPrerender
22
+ };
@@ -1,3 +1,5 @@
1
+ import { renderForPrerender } from "../app/prerender.js";
2
+ import { ensureAsyncRenderScope } from "../render-scope/node-scope.js";
1
3
  import { StaticPaths } from "../../runtime/prerender/static-paths.js";
2
4
  function createDefaultPrerenderer({
3
5
  internals,
@@ -24,8 +26,9 @@ function createDefaultPrerenderer({
24
26
  const staticPaths = new StaticPaths(prerenderer.app);
25
27
  return staticPaths.getAll();
26
28
  },
27
- async render(request, { routeData }) {
28
- return prerenderer.app.render(request, { routeData });
29
+ async render(request, { routeData, collectMetadata }) {
30
+ if (collectMetadata) ensureAsyncRenderScope();
31
+ return renderForPrerender(prerenderer.app, request, { routeData, collectMetadata });
29
32
  },
30
33
  async teardown() {
31
34
  }
@@ -23,6 +23,8 @@ interface RenderToPathPayload {
23
23
  options: StaticBuildOptions;
24
24
  routeToHeaders?: RouteToHeaders;
25
25
  logger: AstroLogger;
26
+ /** Ask the prerenderer to collect and report per-render incremental metadata. */
27
+ collectMetadata?: boolean;
26
28
  }
27
29
  /**
28
30
  * Renders a single prerendered path to an in-memory result.
@@ -48,5 +50,5 @@ interface RenderToPathPayload {
48
50
  * not need to inspect the headers after the call can omit this.
49
51
  * @param params.logger - Logger instance.
50
52
  */
51
- export declare function renderPath({ prerenderer, pathname, route, options, routeToHeaders, logger, }: RenderToPathPayload): Promise<RenderPathResult | null>;
53
+ export declare function renderPath({ prerenderer, pathname, route, options, routeToHeaders, logger, collectMetadata, }: RenderToPathPayload): Promise<RenderPathResult | null>;
52
54
  export {};
@@ -29,11 +29,6 @@ import { routeIsRedirect } from "../routing/helpers.js";
29
29
  import { getOutputFilename } from "../output-filename.js";
30
30
  import { getOutFile, getOutFolder } from "./common.js";
31
31
  import { createDefaultPrerenderer } from "./default-prerenderer.js";
32
- import {
33
- beginContentEntryCollection,
34
- endContentEntryCollection
35
- } from "./incremental-content-collector.js";
36
- import { beginImageCollection, endImageCollection } from "./incremental-image-collector.js";
37
32
  import { IncrementalBuildCache } from "./incremental.js";
38
33
  import { computeConfigHash } from "./config-hash/index.js";
39
34
  import { computeLockfileHash } from "./lockfile/index.js";
@@ -76,26 +71,19 @@ ${colors.bgGreen(colors.black(` ${verb} static routes `))}`);
76
71
  let staticImageList = getStaticImageList();
77
72
  let cache = null;
78
73
  if (options.settings.config.experimental.incrementalBuild) {
79
- if (options.settings.config.build.concurrency > 1) {
80
- logger.warn(
81
- "build",
82
- "The incremental build cache is disabled because `build.concurrency` is greater than 1."
83
- );
84
- } else {
85
- const [configHash, lockfileHash, keyDigest] = await Promise.all([
86
- computeConfigHash(options.settings.config),
87
- computeLockfileHash(fileURLToPath(options.settings.config.root)),
88
- options.key.then(hashCryptoKey)
89
- ]);
90
- cache = IncrementalBuildCache.load(
91
- options.settings,
92
- configHash,
93
- lockfileHash,
94
- keyDigest,
95
- internals.contentEntryRenderHashes ?? /* @__PURE__ */ new Map(),
96
- options.force
97
- );
98
- }
74
+ const [configHash, lockfileHash, keyDigest] = await Promise.all([
75
+ computeConfigHash(options.settings.config),
76
+ computeLockfileHash(fileURLToPath(options.settings.config.root)),
77
+ options.key.then(hashCryptoKey)
78
+ ]);
79
+ cache = IncrementalBuildCache.load(
80
+ options.settings,
81
+ configHash,
82
+ lockfileHash,
83
+ keyDigest,
84
+ internals.contentEntryRenderHashes ?? /* @__PURE__ */ new Map(),
85
+ options.force
86
+ );
99
87
  }
100
88
  try {
101
89
  const pathsWithRoutes = await prerenderer.getStaticPaths();
@@ -277,7 +265,8 @@ async function renderPath({
277
265
  route,
278
266
  options,
279
267
  routeToHeaders = /* @__PURE__ */ new Map(),
280
- logger
268
+ logger,
269
+ collectMetadata
281
270
  }) {
282
271
  const { config } = options.settings;
283
272
  if (route.type === "fallback" && route.pathname !== "/") {
@@ -318,7 +307,7 @@ async function renderPath({
318
307
  let metadata;
319
308
  try {
320
309
  const rendered = normalizePrerenderResult(
321
- await prerenderer.render(request, { routeData: route })
310
+ await prerenderer.render(request, { routeData: route, collectMetadata })
322
311
  );
323
312
  response = rendered.response;
324
313
  metadata = rendered.metadata;
@@ -425,22 +414,17 @@ async function generatePathWithPrerenderer(prerenderer, pathname, route, options
425
414
  if (route.type === "page") {
426
415
  addPageName(pathname, options);
427
416
  }
428
- if (cache) {
429
- beginContentEntryCollection();
430
- beginImageCollection();
431
- }
432
417
  const result = await renderPath({
433
418
  prerenderer,
434
419
  pathname,
435
420
  route,
436
421
  options,
437
422
  routeToHeaders,
438
- logger
423
+ logger,
424
+ collectMetadata: cache !== null
439
425
  });
440
- const collectedContentEntryKeys = cache ? endContentEntryCollection() : void 0;
441
- const collectedStaticImages = cache ? endImageCollection() : void 0;
442
- const contentEntryKeys = result?.metadata?.contentEntryKeys ?? collectedContentEntryKeys;
443
- const staticImages = result?.metadata?.staticImages ?? collectedStaticImages;
426
+ const contentEntryKeys = result?.metadata?.contentEntryKeys;
427
+ const staticImages = result?.metadata?.staticImages;
444
428
  const headers = cache ? [...routeToHeaders.get(pathname)?.headers ?? []] : void 0;
445
429
  if (!result) {
446
430
  logRenderTime(logger, timeStart, true);
@@ -448,7 +432,7 @@ async function generatePathWithPrerenderer(prerenderer, pathname, route, options
448
432
  }
449
433
  await nodeFs.promises.mkdir(result.outFolder, { recursive: true });
450
434
  await nodeFs.promises.writeFile(result.outFile, result.body);
451
- if (cache && cacheKey !== void 0) {
435
+ if (cache && cacheKey !== void 0 && result.metadata !== void 0) {
452
436
  await cache.writeOutputFile(options.settings, relativeOutFile, result.body);
453
437
  cache.record(
454
438
  route.component,
@@ -52,7 +52,18 @@ async function handleCache(state, next) {
52
52
  {
53
53
  request: state.request,
54
54
  url: new URL(state.request.url),
55
- waitUntil: state.renderOptions.waitUntil
55
+ waitUntil: state.renderOptions.waitUntil,
56
+ logger: {
57
+ info(msg) {
58
+ state.logger.info("cache", msg);
59
+ },
60
+ warn(msg) {
61
+ state.logger.warn("cache", msg);
62
+ },
63
+ error(msg) {
64
+ state.logger.error("cache", msg);
65
+ }
66
+ }
56
67
  },
57
68
  async () => {
58
69
  const res = await next();
@@ -89,7 +89,17 @@ function getPathFromCacheKey(key, queryConfig) {
89
89
  const url = new URL(urlPart);
90
90
  return `${url.pathname}${buildQueryString(url, queryConfig)}`;
91
91
  }
92
- const IGNORED_VARY_HEADERS = /* @__PURE__ */ new Set(["cookie", "set-cookie"]);
92
+ const IGNORED_VARY_HEADERS = /* @__PURE__ */ new Set(["set-cookie"]);
93
+ function getUncacheableVaryHeader(response) {
94
+ const vary = response.headers.get("Vary");
95
+ if (!vary) return void 0;
96
+ for (const header of vary.split(",")) {
97
+ const normalized = header.trim().toLowerCase();
98
+ if (normalized === "cookie") return "Cookie";
99
+ if (normalized === "*") return "*";
100
+ }
101
+ return void 0;
102
+ }
93
103
  function parseVaryHeader(response) {
94
104
  const vary = response.headers.get("Vary");
95
105
  if (!vary || vary.trim() === "*") return void 0;
@@ -118,9 +128,14 @@ function hasSetCookieHeader(response) {
118
128
  if (response.headers.has("set-cookie")) return true;
119
129
  return hasAtLeastOneCookie(getCookiesFromResponse(response));
120
130
  }
121
- function warnSkippedSetCookie(url) {
122
- console.warn(
123
- `[astro:cache] Skipping cache for ${url.pathname}${url.search} because response includes Set-Cookie.`
131
+ function warnSkippedSetCookie(logger, url) {
132
+ logger.warn(
133
+ `Skipping cache for ${url.pathname}${url.search} because response includes Set-Cookie.`
134
+ );
135
+ }
136
+ function warnSkippedVary(logger, url, header) {
137
+ logger.warn(
138
+ `Skipping cache for ${url.pathname}${url.search} because response includes Vary: ${header}.`
124
139
  );
125
140
  }
126
141
  class LRUMap {
@@ -232,7 +247,13 @@ const memoryProvider = ((config) => {
232
247
  const { maxAge: newMaxAge, swr: newSwr } = parseCdnCacheControl(cdnCC2);
233
248
  if (newMaxAge > 0) {
234
249
  if (hasSetCookieHeader(freshResponse)) {
235
- warnSkippedSetCookie(requestUrl);
250
+ warnSkippedSetCookie(context.logger, requestUrl);
251
+ return;
252
+ }
253
+ const uncacheableVary = getUncacheableVaryHeader(freshResponse);
254
+ if (uncacheableVary) {
255
+ cache.delete(key);
256
+ warnSkippedVary(context.logger, requestUrl, uncacheableVary);
236
257
  return;
237
258
  }
238
259
  const newTags = parseCacheTags(freshResponse.headers.get("Cache-Tag"));
@@ -249,8 +270,8 @@ const memoryProvider = ((config) => {
249
270
  cache.set(key, newEntry);
250
271
  }
251
272
  }).catch((error) => {
252
- console.warn(
253
- `[astro:cache] Background revalidation failed for ${requestUrl.pathname}${requestUrl.search}: ${String(
273
+ context.logger.warn(
274
+ `Background revalidation failed for ${requestUrl.pathname}${requestUrl.search}: ${String(
254
275
  error
255
276
  )}`
256
277
  );
@@ -266,7 +287,13 @@ const memoryProvider = ((config) => {
266
287
  const { maxAge, swr } = parseCdnCacheControl(cdnCC);
267
288
  if (maxAge > 0) {
268
289
  if (hasSetCookieHeader(response)) {
269
- warnSkippedSetCookie(requestUrl);
290
+ warnSkippedSetCookie(context.logger, requestUrl);
291
+ return response;
292
+ }
293
+ const uncacheableVary = getUncacheableVaryHeader(response);
294
+ if (uncacheableVary) {
295
+ cache.delete(key);
296
+ warnSkippedVary(context.logger, requestUrl, uncacheableVary);
270
297
  return response;
271
298
  }
272
299
  const tags = parseCacheTags(response.headers.get("Cache-Tag"));
@@ -1,4 +1,5 @@
1
1
  import type { MiddlewareNext } from '../../types/public/common.js';
2
+ import type { AstroRuntimeLogger } from '../../types/public/context.js';
2
3
  import type { WaitUntilHook } from '../wait-until.js';
3
4
  export interface CacheOptions {
4
5
  maxAge?: number;
@@ -27,6 +28,7 @@ export interface CacheProvider {
27
28
  request: Request;
28
29
  url: URL;
29
30
  waitUntil?: WaitUntilHook;
31
+ logger: AstroRuntimeLogger;
30
32
  }, next: MiddlewareNext): Promise<Response>;
31
33
  invalidate(options: InvalidateOptions): Promise<void>;
32
34
  }
@@ -34,10 +34,10 @@ export declare const AstroConfigSchema: z.ZodObject<{
34
34
  name: z.ZodString;
35
35
  hooks: z.ZodDefault<z.ZodObject<{}, z.core.$loose>>;
36
36
  }, z.core.$strip>>;
37
- integrations: z.ZodDefault<z.ZodOptional<z.ZodPipe<z.ZodTransform<unknown, unknown>, z.ZodArray<z.ZodObject<{
37
+ integrations: z.ZodDefault<z.ZodOptional<z.ZodPreprocess<z.ZodArray<z.ZodObject<{
38
38
  name: z.ZodString;
39
39
  hooks: z.ZodDefault<z.ZodObject<{}, z.core.$loose>>;
40
- }, z.core.$strip>>>>>;
40
+ }, z.core.$strip>>, unknown>>>;
41
41
  build: z.ZodPrefault<z.ZodObject<{
42
42
  format: z.ZodDefault<z.ZodOptional<z.ZodUnion<readonly [z.ZodLiteral<"file">, z.ZodLiteral<"directory">, z.ZodLiteral<"preserve">]>>>;
43
43
  client: z.ZodPipe<z.ZodDefault<z.ZodOptional<z.ZodString>>, z.ZodTransform<URL, string>>;
@@ -55,13 +55,13 @@ export declare const AstroConfigSchema: z.ZodObject<{
55
55
  }>>>;
56
56
  concurrency: z.ZodDefault<z.ZodOptional<z.ZodNumber>>;
57
57
  }, z.core.$strip>>;
58
- server: z.ZodPrefault<z.ZodPipe<z.ZodTransform<any, unknown>, z.ZodObject<{
58
+ server: z.ZodPrefault<z.ZodPreprocess<z.ZodObject<{
59
59
  open: z.ZodDefault<z.ZodOptional<z.ZodUnion<readonly [z.ZodString, z.ZodBoolean]>>>;
60
60
  host: z.ZodDefault<z.ZodOptional<z.ZodUnion<readonly [z.ZodString, z.ZodBoolean]>>>;
61
61
  port: z.ZodDefault<z.ZodOptional<z.ZodNumber>>;
62
62
  headers: z.ZodOptional<z.ZodCustom<OutgoingHttpHeaders, OutgoingHttpHeaders>>;
63
63
  allowedHosts: z.ZodDefault<z.ZodOptional<z.ZodUnion<readonly [z.ZodArray<z.ZodString>, z.ZodLiteral<true>]>>>;
64
- }, z.core.$strip>>>;
64
+ }, z.core.$strip>, unknown>>;
65
65
  redirects: z.ZodDefault<z.ZodRecord<z.ZodString, z.ZodUnion<readonly [z.ZodString, z.ZodObject<{
66
66
  status: z.ZodUnion<readonly [z.ZodLiteral<300>, z.ZodLiteral<301>, z.ZodLiteral<302>, z.ZodLiteral<303>, z.ZodLiteral<304>, z.ZodLiteral<307>, z.ZodLiteral<308>]>;
67
67
  destination: z.ZodString;
@@ -456,8 +456,8 @@ export declare const AstroConfigSchema: z.ZodObject<{
456
456
  fallbacks: z.ZodOptional<z.ZodArray<z.ZodString>>;
457
457
  optimizedFallbacks: z.ZodOptional<z.ZodBoolean>;
458
458
  display: z.ZodOptional<z.ZodEnum<{
459
- auto: "auto";
460
459
  optional: "optional";
460
+ auto: "auto";
461
461
  fallback: "fallback";
462
462
  block: "block";
463
463
  swap: "swap";
@@ -10,10 +10,10 @@ export declare function createRelativeSchema(cmd: string, fileProtocolRoot: stri
10
10
  name: z.ZodString;
11
11
  hooks: z.ZodDefault<z.ZodObject<{}, z.core.$loose>>;
12
12
  }, z.core.$strip>>;
13
- integrations: z.ZodDefault<z.ZodOptional<z.ZodPipe<z.ZodTransform<unknown, unknown>, z.ZodArray<z.ZodObject<{
13
+ integrations: z.ZodDefault<z.ZodOptional<z.ZodPreprocess<z.ZodArray<z.ZodObject<{
14
14
  name: z.ZodString;
15
15
  hooks: z.ZodDefault<z.ZodObject<{}, z.core.$loose>>;
16
- }, z.core.$strip>>>>>;
16
+ }, z.core.$strip>>, unknown>>>;
17
17
  redirects: z.ZodDefault<z.ZodRecord<z.ZodString, z.ZodUnion<readonly [z.ZodString, z.ZodObject<{
18
18
  status: z.ZodUnion<readonly [z.ZodLiteral<300>, z.ZodLiteral<301>, z.ZodLiteral<302>, z.ZodLiteral<303>, z.ZodLiteral<304>, z.ZodLiteral<307>, z.ZodLiteral<308>]>;
19
19
  destination: z.ZodString;
@@ -408,8 +408,8 @@ export declare function createRelativeSchema(cmd: string, fileProtocolRoot: stri
408
408
  fallbacks: z.ZodOptional<z.ZodArray<z.ZodString>>;
409
409
  optimizedFallbacks: z.ZodOptional<z.ZodBoolean>;
410
410
  display: z.ZodOptional<z.ZodEnum<{
411
- auto: "auto";
412
411
  optional: "optional";
412
+ auto: "auto";
413
413
  fallback: "fallback";
414
414
  block: "block";
415
415
  swap: "swap";
@@ -472,13 +472,13 @@ export declare function createRelativeSchema(cmd: string, fileProtocolRoot: stri
472
472
  }>>>;
473
473
  concurrency: z.ZodDefault<z.ZodOptional<z.ZodNumber>>;
474
474
  }, z.core.$strip>>>;
475
- server: z.ZodPrefault<z.ZodPipe<z.ZodTransform<any, unknown>, z.ZodObject<{
475
+ server: z.ZodPrefault<z.ZodPreprocess<z.ZodObject<{
476
476
  open: z.ZodDefault<z.ZodOptional<z.ZodUnion<readonly [z.ZodString, z.ZodBoolean]>>>;
477
477
  host: z.ZodDefault<z.ZodOptional<z.ZodUnion<readonly [z.ZodString, z.ZodBoolean]>>>;
478
478
  port: z.ZodDefault<z.ZodOptional<z.ZodNumber>>;
479
479
  headers: z.ZodOptional<z.ZodCustom<OutgoingHttpHeaders, OutgoingHttpHeaders>>;
480
480
  allowedHosts: z.ZodDefault<z.ZodOptional<z.ZodUnion<readonly [z.ZodArray<z.ZodString>, z.ZodLiteral<true>]>>>;
481
- }, z.core.$strip>>>;
481
+ }, z.core.$strip>, unknown>>;
482
482
  }, z.core.$strip>, z.ZodTransform<{
483
483
  base: string;
484
484
  trailingSlash: "never" | "ignore" | "always";
@@ -727,7 +727,7 @@ export declare function createRelativeSchema(cmd: string, fileProtocolRoot: stri
727
727
  formats?: ["woff2" | "woff" | "otf" | "ttf" | "eot", ...("woff2" | "woff" | "otf" | "ttf" | "eot")[]] | undefined;
728
728
  fallbacks?: string[] | undefined;
729
729
  optimizedFallbacks?: boolean | undefined;
730
- display?: "auto" | "optional" | "fallback" | "block" | "swap" | undefined;
730
+ display?: "optional" | "auto" | "fallback" | "block" | "swap" | undefined;
731
731
  stretch?: string | undefined;
732
732
  featureSettings?: string | undefined;
733
733
  variationSettings?: string | undefined;
@@ -994,7 +994,7 @@ export declare function createRelativeSchema(cmd: string, fileProtocolRoot: stri
994
994
  formats?: ["woff2" | "woff" | "otf" | "ttf" | "eot", ...("woff2" | "woff" | "otf" | "ttf" | "eot")[]] | undefined;
995
995
  fallbacks?: string[] | undefined;
996
996
  optimizedFallbacks?: boolean | undefined;
997
- display?: "auto" | "optional" | "fallback" | "block" | "swap" | undefined;
997
+ display?: "optional" | "auto" | "fallback" | "block" | "swap" | undefined;
998
998
  stretch?: string | undefined;
999
999
  featureSettings?: string | undefined;
1000
1000
  variationSettings?: string | undefined;
@@ -1,4 +1,4 @@
1
- const ASTRO_VERSION = "7.2.10";
1
+ const ASTRO_VERSION = "7.3.0";
2
2
  const ASTRO_GENERATOR = `Astro v${ASTRO_VERSION}`;
3
3
  const ASTRO_ERROR_HEADER = "X-Astro-Error";
4
4
  const DEFAULT_404_COMPONENT = "astro-default-404.astro";
@@ -1,4 +1,5 @@
1
1
  import type { SerializeOptions } from 'cookie';
2
+ import type { AstroLogger } from '../logger/core.js';
2
3
  export type AstroCookieSetOptions = Pick<SerializeOptions, 'domain' | 'path' | 'expires' | 'maxAge' | 'httpOnly' | 'sameSite' | 'secure' | 'encode' | 'partitioned'>;
3
4
  export interface AstroCookieGetOptions {
4
5
  decode?: (value: string) => string;
@@ -25,7 +26,7 @@ declare class AstroCookie implements AstroCookieInterface {
25
26
  }
26
27
  declare class AstroCookies implements AstroCookiesInterface {
27
28
  #private;
28
- constructor(request: Request);
29
+ constructor(request: Request, logger: Pick<AstroLogger, 'warn'>);
29
30
  /**
30
31
  * Astro.cookies.delete(key) is used to delete a cookie. Using this method will result
31
32
  * in a Set-Cookie header added to the response.
@@ -29,11 +29,13 @@ class AstroCookies {
29
29
  #requestValues;
30
30
  #outgoing;
31
31
  #consumed;
32
- constructor(request) {
32
+ #logger;
33
+ constructor(request, logger) {
33
34
  this.#request = request;
34
35
  this.#requestValues = null;
35
36
  this.#outgoing = null;
36
37
  this.#consumed = false;
38
+ this.#logger = logger;
37
39
  }
38
40
  /**
39
41
  * Astro.cookies.delete(key) is used to delete a cookie. Using this method will result
@@ -112,11 +114,10 @@ class AstroCookies {
112
114
  */
113
115
  set(key, value, options) {
114
116
  if (this.#consumed) {
115
- const warning = new Error(
117
+ this.#logger.warn(
118
+ "SKIP_FORMAT",
116
119
  "Astro.cookies.set() was called after the cookies had already been sent to the browser.\nThis may have happened if this method was called in an imported component.\nPlease make sure that Astro.cookies.set() is only called in the frontmatter of the main page."
117
120
  );
118
- warning.name = "Warning";
119
- console.warn(warning);
120
121
  }
121
122
  let serializedValue;
122
123
  if (typeof value === "string") {
@@ -26,7 +26,7 @@ async function dev(inlineConfig) {
26
26
  await telemetry.record([]);
27
27
  const restart = await createContainerWithAutomaticRestart({ inlineConfig, fs });
28
28
  const logger = restart.container.logger;
29
- const currentVersion = "7.2.10";
29
+ const currentVersion = "7.3.0";
30
30
  const isPrerelease = currentVersion.includes("-");
31
31
  if (!isPrerelease) {
32
32
  try {
@@ -59,7 +59,7 @@ async function dev(inlineConfig) {
59
59
  const chunkSize = getDataStoreChunkSize(restart.container.settings);
60
60
  if (chunkSize !== void 0) {
61
61
  const dataStoreDir = getDataStoreDir(restart.container.settings, true);
62
- store = await MutableDataStore.fromDir(dataStoreDir, chunkSize);
62
+ store = await MutableDataStore.fromDir(dataStoreDir, chunkSize, logger);
63
63
  } else {
64
64
  const dataStoreFile = getDataStoreFile(restart.container.settings, true);
65
65
  store = await MutableDataStore.fromFile(dataStoreFile);
@@ -7,7 +7,7 @@ import { AstroCookies } from '../cookies/index.js';
7
7
  import type { RenderErrorOptions, ResolvedRenderOptions } from '../app/base.js';
8
8
  import type { SSRManifest } from '../app/types.js';
9
9
  import { type RequestLogPayload } from '../environment/index.js';
10
- import type { AstroLogger } from '../logger/core.js';
10
+ import { type AstroLogger } from '../logger/core.js';
11
11
  /**
12
12
  * Per-render facade inputs passed by `BaseApp.render`'s fast path to the
13
13
  * internal `FetchState` constructor and stored as plain state fields.
@@ -35,6 +35,7 @@ import { getRenderOptions } from "../app/render-options.js";
35
35
  import { getFirstForwardedValue, validateForwardedHeaders } from "../app/validate-headers.js";
36
36
  import { getEnvironment } from "../environment/index.js";
37
37
  import { getLogger } from "../logger/manifest-logger.js";
38
+ import { astroToRuntimeLogger } from "../logger/core.js";
38
39
  import { getSite } from "../manifest/derived.js";
39
40
  import { getRouteCache } from "../render/route-cache.js";
40
41
  import { getRouteTable, matchAllRoutes, matchRoute } from "../routing/route-table.js";
@@ -232,7 +233,7 @@ class FetchState {
232
233
  this.clientAddress = options?.clientAddress;
233
234
  this.locals = options?.locals ?? {};
234
235
  this.url = url;
235
- this.cookies = new AstroCookies(request);
236
+ this.cookies = new AstroCookies(request, this.logger);
236
237
  if (manifest.allowedDomains && manifest.allowedDomains.length > 0 && !this.routeData?.prerender) {
237
238
  this.#applyForwardedHeaders();
238
239
  }
@@ -441,17 +442,7 @@ class FetchState {
441
442
  return state.getCsp();
442
443
  },
443
444
  get logger() {
444
- return {
445
- info(msg) {
446
- logger.info(null, msg);
447
- },
448
- warn(msg) {
449
- logger.warn(null, msg);
450
- },
451
- error(msg) {
452
- logger.error(null, msg);
453
- }
454
- };
445
+ return astroToRuntimeLogger(logger);
455
446
  }
456
447
  };
457
448
  this.defineProviderGetters(partial);
@@ -906,17 +897,7 @@ class FetchState {
906
897
  return state.getCsp();
907
898
  },
908
899
  get logger() {
909
- return {
910
- info(msg) {
911
- state.logger.info(null, msg);
912
- },
913
- warn(msg) {
914
- state.logger.warn(null, msg);
915
- },
916
- error(msg) {
917
- state.logger.error(null, msg);
918
- }
919
- };
900
+ return astroToRuntimeLogger(state.logger);
920
901
  }
921
902
  };
922
903
  this.defineProviderGetters(ctx);
@@ -1,3 +1,4 @@
1
+ import type { AstroRuntimeLogger } from '../../types/public/context.js';
1
2
  export interface AstroLoggerDestination {
2
3
  /**
3
4
  * It receives a message and writes it into a destination
@@ -109,4 +110,5 @@ export declare class AstroIntegrationLogger {
109
110
  */
110
111
  close(): void;
111
112
  }
113
+ export declare function astroToRuntimeLogger(logger: AstroLogger): AstroRuntimeLogger;
112
114
  export {};
@@ -186,9 +186,23 @@ class AstroIntegrationLogger {
186
186
  }
187
187
  }
188
188
  }
189
+ function astroToRuntimeLogger(logger) {
190
+ return {
191
+ info(msg) {
192
+ logger.info(null, msg);
193
+ },
194
+ warn(msg) {
195
+ logger.warn(null, msg);
196
+ },
197
+ error(msg) {
198
+ logger.error(null, msg);
199
+ }
200
+ };
201
+ }
189
202
  export {
190
203
  AstroIntegrationLogger,
191
204
  AstroLogger,
205
+ astroToRuntimeLogger,
192
206
  dateTimeFormat,
193
207
  debug,
194
208
  getEventPrefix,
@@ -24,7 +24,18 @@ export declare function emitDestination(config: NormalizedLoggerConfig, resolveE
24
24
  * destinations continue numbering where their parent left off.
25
25
  */
26
26
  nameOffset?: number): Promise<EmittedDestination>;
27
- export declare function vitePluginLogger({ settings, }: {
27
+ /**
28
+ * Emits `virtual:astro:logger`: the configured destination as the default export
29
+ * (`null` when the user configured none) plus the resolved log level.
30
+ *
31
+ * The module is always registered, even without a `logger` config, so that code
32
+ * generated ahead of the user's config — `astro:content`, which is built from a
33
+ * static template — can import it unconditionally. It deliberately imports
34
+ * nothing but the user's destination entrypoint: unlike `virtual:astro:manifest`
35
+ * it is a leaf, so reaching a logger through it cannot pull renderers and pages
36
+ * into an importer's module graph.
37
+ */
38
+ export declare function vitePluginLogger({ settings }: {
28
39
  settings: AstroSettings;
29
- }): VitePlugin | undefined;
40
+ }): VitePlugin;
30
41
  export {};