@sveltejs/kit 2.17.3 → 2.18.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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sveltejs/kit",
3
- "version": "2.17.3",
3
+ "version": "2.18.0",
4
4
  "description": "SvelteKit is the fastest way to build Svelte apps",
5
5
  "keywords": [
6
6
  "framework",
@@ -36,7 +36,7 @@
36
36
  "@types/connect": "^3.4.38",
37
37
  "@types/node": "^18.19.48",
38
38
  "@types/set-cookie-parser": "^2.4.7",
39
- "dts-buddy": "^0.5.4",
39
+ "dts-buddy": "^0.5.5",
40
40
  "rollup": "^4.14.2",
41
41
  "svelte": "^5.2.9",
42
42
  "svelte-preprocess": "^6.0.0",
@@ -41,6 +41,7 @@ export function find_server_assets(build_data, routes) {
41
41
 
42
42
  for (const n of used_nodes) {
43
43
  const node = build_data.manifest_data.nodes[n];
44
+ if (node?.universal) add_assets(node.universal);
44
45
  if (node?.server) add_assets(node.server);
45
46
  }
46
47
 
@@ -27,12 +27,10 @@ export function generate_manifest({ build_data, prerendered, relative_path, rout
27
27
  const reindexed = new Map();
28
28
  /**
29
29
  * All nodes actually used in the routes definition (prerendered routes are omitted).
30
- * If `routes` is empty, it means that this manifest is only used for server-side resolution
31
- * and the root layout/error is therefore not needed.
32
- * Else, root layout/error is always included as they are needed for 404 and root errors.
30
+ * Root layout/error is always included as they are needed for 404 and root errors.
33
31
  * @type {Set<any>}
34
32
  */
35
- const used_nodes = new Set(routes.length > 0 ? [0, 1] : []);
33
+ const used_nodes = new Set([0, 1]);
36
34
 
37
35
  const server_assets = find_server_assets(build_data, routes);
38
36
 
@@ -1,5 +1,13 @@
1
1
  import { HttpError, Redirect, ActionFailure } from '../runtime/control.js';
2
2
  import { BROWSER, DEV } from 'esm-env';
3
+ import {
4
+ add_data_suffix,
5
+ add_resolution_suffix,
6
+ has_data_suffix,
7
+ has_resolution_suffix,
8
+ strip_data_suffix,
9
+ strip_resolution_suffix
10
+ } from '../runtime/pathname.js';
3
11
 
4
12
  export { VERSION } from '../version.js';
5
13
 
@@ -207,3 +215,49 @@ export function fail(status, data) {
207
215
  export function isActionFailure(e) {
208
216
  return e instanceof ActionFailure;
209
217
  }
218
+
219
+ /**
220
+ * Strips possible SvelteKit-internal suffixes and trailing slashes from the URL pathname.
221
+ * Returns the normalized URL as well as a method for adding the potential suffix back
222
+ * based on a new pathname (possibly including search) or URL.
223
+ * ```js
224
+ * import { normalizeUrl } from '@sveltejs/kit';
225
+ *
226
+ * const { url, denormalize } = normalizeUrl('/blog/post/__data.json');
227
+ * console.log(url.pathname); // /blog/post
228
+ * console.log(denormalize('/blog/post/a')); // /blog/post/a/__data.json
229
+ * ```
230
+ * @param {URL | string} url
231
+ * @returns {{ url: URL, wasNormalized: boolean, denormalize: (url?: string | URL) => URL }}
232
+ */
233
+ export function normalizeUrl(url) {
234
+ url = new URL(url, 'http://internal');
235
+
236
+ const is_route_resolution = has_resolution_suffix(url.pathname);
237
+ const is_data_request = has_data_suffix(url.pathname);
238
+ const has_trailing_slash = url.pathname !== '/' && url.pathname.endsWith('/');
239
+
240
+ if (is_route_resolution) {
241
+ url.pathname = strip_resolution_suffix(url.pathname);
242
+ } else if (is_data_request) {
243
+ url.pathname = strip_data_suffix(url.pathname);
244
+ } else if (has_trailing_slash) {
245
+ url.pathname = url.pathname.slice(0, -1);
246
+ }
247
+
248
+ return {
249
+ url,
250
+ wasNormalized: is_data_request || is_route_resolution || has_trailing_slash,
251
+ denormalize: (new_url = url) => {
252
+ new_url = new URL(new_url, url);
253
+ if (is_route_resolution) {
254
+ new_url.pathname = add_resolution_suffix(new_url.pathname);
255
+ } else if (is_data_request) {
256
+ new_url.pathname = add_data_suffix(new_url.pathname);
257
+ } else if (has_trailing_slash && !new_url.pathname.endsWith('/')) {
258
+ new_url.pathname += '/';
259
+ }
260
+ return new_url;
261
+ }
262
+ };
263
+ }
@@ -814,7 +814,7 @@ export type ClientInit = () => MaybePromise<void>;
814
814
  * The [`reroute`](https://svelte.dev/docs/kit/hooks#Universal-hooks-reroute) hook allows you to modify the URL before it is used to determine which route to render.
815
815
  * @since 2.3.0
816
816
  */
817
- export type Reroute = (event: { url: URL }) => void | string;
817
+ export type Reroute = (event: { url: URL }) => MaybePromise<void | string>;
818
818
 
819
819
  /**
820
820
  * The [`transport`](https://svelte.dev/docs/kit/hooks#Universal-hooks-transport) hook allows you to transport custom types across the server/client boundary.
@@ -1177,7 +1177,7 @@ export interface RequestEvent<
1177
1177
  * - During server-side rendering, the response will be captured and inlined into the rendered HTML by hooking into the `text` and `json` methods of the `Response` object. Note that headers will _not_ be serialized, unless explicitly included via [`filterSerializedResponseHeaders`](https://svelte.dev/docs/kit/hooks#Server-hooks-handle)
1178
1178
  * - During hydration, the response will be read from the HTML, guaranteeing consistency and preventing an additional network request.
1179
1179
  *
1180
- * You can learn more about making credentialed requests with cookies [here](https://svelte.dev/docs/kit/load#Cookies)
1180
+ * You can learn more about making credentialed requests with cookies [here](https://svelte.dev/docs/kit/load#Cookies).
1181
1181
  */
1182
1182
  fetch: typeof fetch;
1183
1183
  /**
@@ -1189,7 +1189,7 @@ export interface RequestEvent<
1189
1189
  */
1190
1190
  locals: App.Locals;
1191
1191
  /**
1192
- * The parameters of the current route - e.g. for a route like `/blog/[slug]`, a `{ slug: string }` object
1192
+ * The parameters of the current route - e.g. for a route like `/blog/[slug]`, a `{ slug: string }` object.
1193
1193
  */
1194
1194
  params: Params;
1195
1195
  /**
@@ -1197,15 +1197,15 @@ export interface RequestEvent<
1197
1197
  */
1198
1198
  platform: Readonly<App.Platform> | undefined;
1199
1199
  /**
1200
- * The original request object
1200
+ * The original request object.
1201
1201
  */
1202
1202
  request: Request;
1203
1203
  /**
1204
- * Info about the current route
1204
+ * Info about the current route.
1205
1205
  */
1206
1206
  route: {
1207
1207
  /**
1208
- * The ID of the current route - e.g. for `src/routes/blog/[slug]`, it would be `/blog/[slug]`
1208
+ * The ID of the current route - e.g. for `src/routes/blog/[slug]`, it would be `/blog/[slug]`.
1209
1209
  */
1210
1210
  id: RouteId;
1211
1211
  };
@@ -1302,15 +1302,16 @@ export class Server {
1302
1302
  }
1303
1303
 
1304
1304
  export interface ServerInitOptions {
1305
- /** A map of environment variables */
1305
+ /** A map of environment variables. */
1306
1306
  env: Record<string, string>;
1307
- /** A function that turns an asset filename into a `ReadableStream`. Required for the `read` export from `$app/server` to work */
1307
+ /** A function that turns an asset filename into a `ReadableStream`. Required for the `read` export from `$app/server` to work. */
1308
1308
  read?: (file: string) => ReadableStream;
1309
1309
  }
1310
1310
 
1311
1311
  export interface SSRManifest {
1312
1312
  appDir: string;
1313
1313
  appPath: string;
1314
+ /** Static files from `kit.config.files.assets` and the service worker (if any). */
1314
1315
  assets: Set<string>;
1315
1316
  mimeTypes: Record<string, string>;
1316
1317
 
@@ -1321,7 +1322,7 @@ export interface SSRManifest {
1321
1322
  routes: SSRRoute[];
1322
1323
  prerendered_routes: Set<string>;
1323
1324
  matchers: () => Promise<Record<string, ParamMatcher>>;
1324
- /** A `[file]: size` map of all assets imported by server code */
1325
+ /** A `[file]: size` map of all assets imported by server code. */
1325
1326
  server_assets: Record<string, number>;
1326
1327
  };
1327
1328
  }
@@ -1452,7 +1453,7 @@ export interface HttpError {
1452
1453
  }
1453
1454
 
1454
1455
  /**
1455
- * The object returned by the [`redirect`](https://svelte.dev/docs/kit/@sveltejs-kit#redirect) function
1456
+ * The object returned by the [`redirect`](https://svelte.dev/docs/kit/@sveltejs-kit#redirect) function.
1456
1457
  */
1457
1458
  export interface Redirect {
1458
1459
  /** The [HTTP status code](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status#redirection_messages), in the range 300-308. */
@@ -177,17 +177,18 @@ export async function dev(vite, vite_config, svelte_config) {
177
177
  return async () => {
178
178
  /** @type {import('types').SSRNode} */
179
179
  const result = {};
180
-
181
- /** @type {import('vite').ModuleNode[]} */
182
- const module_nodes = [];
183
-
184
180
  result.index = index;
181
+ result.universal_id = node.universal;
182
+ result.server_id = node.server;
185
183
 
186
- // these are unused in dev, it's easier to include them
184
+ // these are unused in dev, but it's easier to include them
187
185
  result.imports = [];
188
186
  result.stylesheets = [];
189
187
  result.fonts = [];
190
188
 
189
+ /** @type {import('vite').ModuleNode[]} */
190
+ const module_nodes = [];
191
+
191
192
  if (node.component) {
192
193
  result.component = async () => {
193
194
  const { module_node, module } = await resolve(
@@ -202,17 +203,13 @@ export async function dev(vite, vite_config, svelte_config) {
202
203
 
203
204
  if (node.universal) {
204
205
  const { module, module_node } = await resolve(node.universal);
205
-
206
206
  module_nodes.push(module_node);
207
-
208
207
  result.universal = module;
209
- result.universal_id = node.universal;
210
208
  }
211
209
 
212
210
  if (node.server) {
213
211
  const { module } = await resolve(node.server);
214
212
  result.server = module;
215
- result.server_id = node.server;
216
213
  }
217
214
 
218
215
  // in dev we inline all styles to avoid FOUC. this gets populated lazily so that
@@ -1198,13 +1198,13 @@ async function load_root_error_page({ status, error, url, route }) {
1198
1198
  /**
1199
1199
  * Resolve the relative rerouted URL for a client-side navigation
1200
1200
  * @param {URL} url
1201
- * @returns {URL | undefined}
1201
+ * @returns {Promise<URL | undefined>}
1202
1202
  */
1203
- function get_rerouted_url(url) {
1204
- // reroute could alter the given URL, so we pass a copy
1203
+ async function get_rerouted_url(url) {
1205
1204
  let rerouted;
1206
1205
  try {
1207
- rerouted = app.hooks.reroute({ url: new URL(url) }) ?? url;
1206
+ // reroute could alter the given URL, so we pass a copy
1207
+ rerouted = (await app.hooks.reroute({ url: new URL(url) })) ?? url;
1208
1208
 
1209
1209
  if (typeof rerouted === 'string') {
1210
1210
  const tmp = new URL(url); // do not mutate the incoming URL
@@ -1246,7 +1246,7 @@ async function get_navigation_intent(url, invalidating) {
1246
1246
  if (is_external_url(url, base, app.hash)) return;
1247
1247
 
1248
1248
  if (__SVELTEKIT_CLIENT_ROUTING__) {
1249
- const rerouted = get_rerouted_url(url);
1249
+ const rerouted = await get_rerouted_url(url);
1250
1250
  if (!rerouted) return;
1251
1251
 
1252
1252
  const path = get_url_path(rerouted);
@@ -1636,25 +1636,29 @@ if (import.meta.hot) {
1636
1636
  });
1637
1637
  }
1638
1638
 
1639
+ /** @typedef {(typeof PRELOAD_PRIORITIES)['hover'] | (typeof PRELOAD_PRIORITIES)['tap']} PreloadDataPriority */
1640
+
1639
1641
  function setup_preload() {
1640
1642
  /** @type {NodeJS.Timeout} */
1641
1643
  let mousemove_timeout;
1642
1644
  /** @type {Element} */
1643
1645
  let current_a;
1646
+ /** @type {PreloadDataPriority} */
1647
+ let current_priority;
1644
1648
 
1645
1649
  container.addEventListener('mousemove', (event) => {
1646
1650
  const target = /** @type {Element} */ (event.target);
1647
1651
 
1648
1652
  clearTimeout(mousemove_timeout);
1649
1653
  mousemove_timeout = setTimeout(() => {
1650
- void preload(target, 2);
1654
+ void preload(target, PRELOAD_PRIORITIES.hover);
1651
1655
  }, 20);
1652
1656
  });
1653
1657
 
1654
1658
  /** @param {Event} event */
1655
1659
  function tap(event) {
1656
1660
  if (event.defaultPrevented) return;
1657
- void preload(/** @type {Element} */ (event.composedPath()[0]), 1);
1661
+ void preload(/** @type {Element} */ (event.composedPath()[0]), PRELOAD_PRIORITIES.tap);
1658
1662
  }
1659
1663
 
1660
1664
  container.addEventListener('mousedown', tap);
@@ -1674,11 +1678,14 @@ function setup_preload() {
1674
1678
 
1675
1679
  /**
1676
1680
  * @param {Element} element
1677
- * @param {number} priority
1681
+ * @param {PreloadDataPriority} priority
1678
1682
  */
1679
1683
  async function preload(element, priority) {
1680
1684
  const a = find_anchor(element, container);
1681
- if (!a || a === current_a) return;
1685
+
1686
+ // we don't want to preload data again if the user has already hovered/tapped
1687
+ const interacted = a === current_a && priority >= current_priority;
1688
+ if (!a || interacted) return;
1682
1689
 
1683
1690
  const { url, external, download } = get_link_info(a, base, app.hash);
1684
1691
  if (external || download) return;
@@ -1687,31 +1694,34 @@ function setup_preload() {
1687
1694
 
1688
1695
  // we don't want to preload data for a page we're already on
1689
1696
  const same_url = url && get_page_key(current.url) === get_page_key(url);
1690
-
1691
- if (!options.reload && !same_url) {
1692
- if (priority <= options.preload_data) {
1693
- current_a = a;
1694
- const intent = await get_navigation_intent(url, false);
1695
- if (intent) {
1696
- if (DEV) {
1697
- void _preload_data(intent).then((result) => {
1698
- if (result.type === 'loaded' && result.state.error) {
1699
- console.warn(
1700
- `Preloading data for ${intent.url.pathname} failed with the following error: ${result.state.error.message}\n` +
1701
- 'If this error is transient, you can ignore it. Otherwise, consider disabling preloading for this route. ' +
1702
- 'This route was preloaded due to a data-sveltekit-preload-data attribute. ' +
1703
- 'See https://svelte.dev/docs/kit/link-options for more info'
1704
- );
1705
- }
1706
- });
1707
- } else {
1708
- void _preload_data(intent);
1697
+ if (options.reload || same_url) return;
1698
+
1699
+ if (priority <= options.preload_data) {
1700
+ current_a = a;
1701
+ // we don't want to preload data again on tap if we've already preloaded it on hover
1702
+ current_priority = PRELOAD_PRIORITIES.tap;
1703
+
1704
+ const intent = await get_navigation_intent(url, false);
1705
+ if (!intent) return;
1706
+
1707
+ if (DEV) {
1708
+ void _preload_data(intent).then((result) => {
1709
+ if (result.type === 'loaded' && result.state.error) {
1710
+ console.warn(
1711
+ `Preloading data for ${intent.url.pathname} failed with the following error: ${result.state.error.message}\n` +
1712
+ 'If this error is transient, you can ignore it. Otherwise, consider disabling preloading for this route. ' +
1713
+ 'This route was preloaded due to a data-sveltekit-preload-data attribute. ' +
1714
+ 'See https://svelte.dev/docs/kit/link-options for more info'
1715
+ );
1709
1716
  }
1710
- }
1711
- } else if (priority <= options.preload_code) {
1712
- current_a = a;
1713
- void _preload_code(/** @type {URL} */ (url));
1717
+ });
1718
+ } else {
1719
+ void _preload_data(intent);
1714
1720
  }
1721
+ } else if (priority <= options.preload_code) {
1722
+ current_a = a;
1723
+ current_priority = priority;
1724
+ void _preload_code(/** @type {URL} */ (url));
1715
1725
  }
1716
1726
  }
1717
1727
 
@@ -1997,7 +2007,7 @@ export async function preloadCode(pathname) {
1997
2007
  }
1998
2008
 
1999
2009
  if (__SVELTEKIT_CLIENT_ROUTING__) {
2000
- const rerouted = get_rerouted_url(url);
2010
+ const rerouted = await get_rerouted_url(url);
2001
2011
  if (!rerouted || !routes.find((route) => route.exec(get_url_path(rerouted)))) {
2002
2012
  throw new Error(`'${pathname}' did not match any routes`);
2003
2013
  }
@@ -2435,6 +2445,12 @@ function _start_router() {
2435
2445
  if (!hash_navigating) {
2436
2446
  const url = new URL(location.href);
2437
2447
  update_url(url);
2448
+
2449
+ // if the user edits the hash via the browser URL bar, trigger a full-page
2450
+ // reload to align with pathname router behavior
2451
+ if (app.hash) {
2452
+ location.reload();
2453
+ }
2438
2454
  }
2439
2455
  }
2440
2456
  });
@@ -2453,13 +2469,6 @@ function _start_router() {
2453
2469
  '',
2454
2470
  location.href
2455
2471
  );
2456
- } else if (app.hash) {
2457
- // If the user edits the hash via the browser URL bar, it
2458
- // (surprisingly!) mutates `current.url`, allowing us to
2459
- // detect it and trigger a navigation
2460
- if (current.url.hash === location.hash) {
2461
- void navigate({ type: 'goto', url: decode_hash(current.url) });
2462
- }
2463
2472
  }
2464
2473
  });
2465
2474
 
@@ -78,7 +78,7 @@ export async function load_server_data({ event, state, node, parent }) {
78
78
  const { href } = new URL(dep, event.url);
79
79
 
80
80
  if (DEV) {
81
- validate_depends(node.server_id, dep);
81
+ validate_depends(node.server_id || 'missing route ID', dep);
82
82
 
83
83
  if (done && !uses.dependencies.has(href)) {
84
84
  console.warn(
@@ -115,7 +115,7 @@ export async function respond(request, options, manifest, state) {
115
115
 
116
116
  try {
117
117
  // reroute could alter the given URL, so we pass a copy
118
- resolved_path = options.hooks.reroute({ url: new URL(url) }) ?? url.pathname;
118
+ resolved_path = (await options.hooks.reroute({ url: new URL(url) })) ?? url.pathname;
119
119
  } catch {
120
120
  return text('Internal Server Error', {
121
121
  status: 500
@@ -68,24 +68,24 @@ export interface BuildData {
68
68
  out_dir: string;
69
69
  service_worker: string | null;
70
70
  client: {
71
- /** Path to the client entry point */
71
+ /** Path to the client entry point. */
72
72
  start: string;
73
- /** Path to the generated `app.js` file that contains the client manifest. Only set in case of `bundleStrategy === 'split'` */
73
+ /** Path to the generated `app.js` file that contains the client manifest. Only set in case of `bundleStrategy === 'split'`. */
74
74
  app?: string;
75
- /** JS files that the client entry point relies on */
75
+ /** JS files that the client entry point relies on. */
76
76
  imports: string[];
77
77
  /**
78
78
  * JS files that represent the entry points of the layouts/pages.
79
79
  * An entry is undefined if the layout/page has no component or universal file (i.e. only has a `.server.js` file).
80
80
  * Only set in case of `router.resolution === 'server'`.
81
81
  */
82
- nodes?: (string | undefined)[];
82
+ nodes?: Array<string | undefined>;
83
83
  /**
84
84
  * CSS files referenced in the entry points of the layouts/pages.
85
85
  * An entry is undefined if the layout/page has no component or universal file (i.e. only has a `.server.js` file) or if has no CSS.
86
86
  * Only set in case of `router.resolution === 'server'`.
87
87
  */
88
- css?: (string[] | undefined)[];
88
+ css?: Array<string[] | undefined>;
89
89
  /**
90
90
  * Contains the client route manifest in a form suitable for the server which is used for server side route resolution.
91
91
  * Notably, it contains all routes, regardless of whether they are prerendered or not (those are missing in the optimized server route manifest).
@@ -95,7 +95,7 @@ export interface BuildData {
95
95
  stylesheets: string[];
96
96
  fonts: string[];
97
97
  uses_env_dynamic_public: boolean;
98
- /** Only set in case of `bundleStrategy === 'inline'` */
98
+ /** Only set in case of `bundleStrategy === 'inline'`. */
99
99
  inline?: {
100
100
  script: string;
101
101
  style: string | undefined;
@@ -172,7 +172,7 @@ export class InternalServer extends Server {
172
172
  options: RequestOptions & {
173
173
  prerendering?: PrerenderOptions;
174
174
  read: (file: string) => Buffer;
175
- /** A hook called before `handle` during dev, so that `AsyncLocalStorage` can be populated */
175
+ /** A hook called before `handle` during dev, so that `AsyncLocalStorage` can be populated. */
176
176
  before_handle?: (event: RequestEvent, config: any, prerender: PrerenderOption) => void;
177
177
  emulator?: Emulator;
178
178
  }
@@ -180,6 +180,7 @@ export class InternalServer extends Server {
180
180
  }
181
181
 
182
182
  export interface ManifestData {
183
+ /** Static files from `kit.config.files.assets`. */
183
184
  assets: Asset[];
184
185
  hooks: {
185
186
  client: string | null;
@@ -193,15 +194,15 @@ export interface ManifestData {
193
194
 
194
195
  export interface PageNode {
195
196
  depth: number;
196
- /** The +page/layout.svelte */
197
+ /** The `+page/layout.svelte`. */
197
198
  component?: string; // TODO supply default component if it's missing (bit of an edge case)
198
- /** The +page/layout.js/.ts */
199
+ /** The `+page/layout.js/.ts`. */
199
200
  universal?: string;
200
- /** The +page/layout.server.js/ts */
201
+ /** The `+page/layout.server.js/ts`. */
201
202
  server?: string;
202
203
  parent_id?: string;
203
204
  parent?: PageNode;
204
- /** Filled with the pages that reference this layout (if this is a layout) */
205
+ /** Filled with the pages that reference this layout (if this is a layout). */
205
206
  child_pages?: PageNode[];
206
207
  }
207
208
 
@@ -219,6 +220,7 @@ export interface PrerenderOptions {
219
220
  export type RecursiveRequired<T> = {
220
221
  // Recursive implementation of TypeScript's Required utility type.
221
222
  // Will recursively continue until it reaches a primitive or Function
223
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-function-type
222
224
  [K in keyof T]-?: Extract<T[K], Function> extends never // If it does not have a Function type
223
225
  ? RecursiveRequired<T[K]> // recursively continue through.
224
226
  : T[K]; // Use the exact type for everything else
@@ -305,20 +307,20 @@ export interface ServerDataChunkNode {
305
307
 
306
308
  /**
307
309
  * Signals that the server `load` function was not run, and the
308
- * client should use what it has in memory
310
+ * client should use what it has in memory.
309
311
  */
310
312
  export interface ServerDataSkippedNode {
311
313
  type: 'skip';
312
314
  }
313
315
 
314
316
  /**
315
- * Signals that the server `load` function failed
317
+ * Signals that the server `load` function failed.
316
318
  */
317
319
  export interface ServerErrorNode {
318
320
  type: 'error';
319
321
  error: App.Error;
320
322
  /**
321
- * Only set for HttpErrors
323
+ * Only set for HttpErrors.
322
324
  */
323
325
  status?: number;
324
326
  }
@@ -338,7 +340,7 @@ export interface ServerMetadataRoute {
338
340
 
339
341
  export interface ServerMetadata {
340
342
  nodes: Array<{
341
- /** Also `true` when using `trailingSlash`, because we need to do a server request in that case to get its value */
343
+ /** Also `true` when using `trailingSlash`, because we need to do a server request in that case to get its value. */
342
344
  has_server_load: boolean;
343
345
  }>;
344
346
  routes: Map<string, ServerMetadataRoute>;
@@ -364,7 +366,7 @@ export type SSRComponentLoader = () => Promise<SSRComponent>;
364
366
 
365
367
  export interface SSRNode {
366
368
  component: SSRComponentLoader;
367
- /** index into the `nodes` array in the generated `client/app.js` */
369
+ /** index into the `nodes` array in the generated `client/app.js`. */
368
370
  index: number;
369
371
  /** external JS files that are loaded on the client. `imports[0]` is the entry point (e.g. `client/nodes/0.js`) */
370
372
  imports: string[];
@@ -372,7 +374,7 @@ export interface SSRNode {
372
374
  stylesheets: string[];
373
375
  /** external font files that are loaded on the client */
374
376
  fonts: string[];
375
- /** inlined styles */
377
+ /** inlined styles. */
376
378
  inline_styles?(): MaybePromise<Record<string, string>>;
377
379
 
378
380
  universal: {
@@ -396,8 +398,8 @@ export interface SSRNode {
396
398
  entries?: PrerenderEntryGenerator;
397
399
  };
398
400
 
399
- universal_id: string;
400
- server_id: string;
401
+ universal_id?: string;
402
+ server_id?: string;
401
403
  }
402
404
 
403
405
  export type SSRNodeLoader = () => Promise<SSRNode>;
@@ -465,18 +467,18 @@ export interface SSRState {
465
467
  fallback?: string;
466
468
  getClientAddress(): string;
467
469
  /**
468
- * True if we're currently attempting to render an error page
470
+ * True if we're currently attempting to render an error page.
469
471
  */
470
472
  error: boolean;
471
473
  /**
472
- * Allows us to prevent `event.fetch` from making infinitely looping internal requests
474
+ * Allows us to prevent `event.fetch` from making infinitely looping internal requests.
473
475
  */
474
476
  depth: number;
475
477
  platform?: any;
476
478
  prerendering?: PrerenderOptions;
477
479
  /**
478
480
  * When fetching data from a +server.js endpoint in `load`, the page's
479
- * prerender option is inherited by the endpoint, unless overridden
481
+ * prerender option is inherited by the endpoint, unless overridden.
480
482
  */
481
483
  prerender_default?: PrerenderOption;
482
484
  read?: (file: string) => Buffer;
package/src/version.js CHANGED
@@ -1,4 +1,4 @@
1
1
  // generated during release, do not modify
2
2
 
3
3
  /** @type {string} */
4
- export const VERSION = '2.17.3';
4
+ export const VERSION = '2.18.0';
package/types/index.d.ts CHANGED
@@ -796,7 +796,7 @@ declare module '@sveltejs/kit' {
796
796
  * The [`reroute`](https://svelte.dev/docs/kit/hooks#Universal-hooks-reroute) hook allows you to modify the URL before it is used to determine which route to render.
797
797
  * @since 2.3.0
798
798
  */
799
- export type Reroute = (event: { url: URL }) => void | string;
799
+ export type Reroute = (event: { url: URL }) => MaybePromise<void | string>;
800
800
 
801
801
  /**
802
802
  * The [`transport`](https://svelte.dev/docs/kit/hooks#Universal-hooks-transport) hook allows you to transport custom types across the server/client boundary.
@@ -1159,7 +1159,7 @@ declare module '@sveltejs/kit' {
1159
1159
  * - During server-side rendering, the response will be captured and inlined into the rendered HTML by hooking into the `text` and `json` methods of the `Response` object. Note that headers will _not_ be serialized, unless explicitly included via [`filterSerializedResponseHeaders`](https://svelte.dev/docs/kit/hooks#Server-hooks-handle)
1160
1160
  * - During hydration, the response will be read from the HTML, guaranteeing consistency and preventing an additional network request.
1161
1161
  *
1162
- * You can learn more about making credentialed requests with cookies [here](https://svelte.dev/docs/kit/load#Cookies)
1162
+ * You can learn more about making credentialed requests with cookies [here](https://svelte.dev/docs/kit/load#Cookies).
1163
1163
  */
1164
1164
  fetch: typeof fetch;
1165
1165
  /**
@@ -1171,7 +1171,7 @@ declare module '@sveltejs/kit' {
1171
1171
  */
1172
1172
  locals: App.Locals;
1173
1173
  /**
1174
- * The parameters of the current route - e.g. for a route like `/blog/[slug]`, a `{ slug: string }` object
1174
+ * The parameters of the current route - e.g. for a route like `/blog/[slug]`, a `{ slug: string }` object.
1175
1175
  */
1176
1176
  params: Params;
1177
1177
  /**
@@ -1179,15 +1179,15 @@ declare module '@sveltejs/kit' {
1179
1179
  */
1180
1180
  platform: Readonly<App.Platform> | undefined;
1181
1181
  /**
1182
- * The original request object
1182
+ * The original request object.
1183
1183
  */
1184
1184
  request: Request;
1185
1185
  /**
1186
- * Info about the current route
1186
+ * Info about the current route.
1187
1187
  */
1188
1188
  route: {
1189
1189
  /**
1190
- * The ID of the current route - e.g. for `src/routes/blog/[slug]`, it would be `/blog/[slug]`
1190
+ * The ID of the current route - e.g. for `src/routes/blog/[slug]`, it would be `/blog/[slug]`.
1191
1191
  */
1192
1192
  id: RouteId;
1193
1193
  };
@@ -1284,15 +1284,16 @@ declare module '@sveltejs/kit' {
1284
1284
  }
1285
1285
 
1286
1286
  export interface ServerInitOptions {
1287
- /** A map of environment variables */
1287
+ /** A map of environment variables. */
1288
1288
  env: Record<string, string>;
1289
- /** A function that turns an asset filename into a `ReadableStream`. Required for the `read` export from `$app/server` to work */
1289
+ /** A function that turns an asset filename into a `ReadableStream`. Required for the `read` export from `$app/server` to work. */
1290
1290
  read?: (file: string) => ReadableStream;
1291
1291
  }
1292
1292
 
1293
1293
  export interface SSRManifest {
1294
1294
  appDir: string;
1295
1295
  appPath: string;
1296
+ /** Static files from `kit.config.files.assets` and the service worker (if any). */
1296
1297
  assets: Set<string>;
1297
1298
  mimeTypes: Record<string, string>;
1298
1299
 
@@ -1303,7 +1304,7 @@ declare module '@sveltejs/kit' {
1303
1304
  routes: SSRRoute[];
1304
1305
  prerendered_routes: Set<string>;
1305
1306
  matchers: () => Promise<Record<string, ParamMatcher>>;
1306
- /** A `[file]: size` map of all assets imported by server code */
1307
+ /** A `[file]: size` map of all assets imported by server code. */
1307
1308
  server_assets: Record<string, number>;
1308
1309
  };
1309
1310
  }
@@ -1434,7 +1435,7 @@ declare module '@sveltejs/kit' {
1434
1435
  }
1435
1436
 
1436
1437
  /**
1437
- * The object returned by the [`redirect`](https://svelte.dev/docs/kit/@sveltejs-kit#redirect) function
1438
+ * The object returned by the [`redirect`](https://svelte.dev/docs/kit/@sveltejs-kit#redirect) function.
1438
1439
  */
1439
1440
  export interface Redirect {
1440
1441
  /** The [HTTP status code](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status#redirection_messages), in the range 300-308. */
@@ -1715,24 +1716,24 @@ declare module '@sveltejs/kit' {
1715
1716
  out_dir: string;
1716
1717
  service_worker: string | null;
1717
1718
  client: {
1718
- /** Path to the client entry point */
1719
+ /** Path to the client entry point. */
1719
1720
  start: string;
1720
- /** Path to the generated `app.js` file that contains the client manifest. Only set in case of `bundleStrategy === 'split'` */
1721
+ /** Path to the generated `app.js` file that contains the client manifest. Only set in case of `bundleStrategy === 'split'`. */
1721
1722
  app?: string;
1722
- /** JS files that the client entry point relies on */
1723
+ /** JS files that the client entry point relies on. */
1723
1724
  imports: string[];
1724
1725
  /**
1725
1726
  * JS files that represent the entry points of the layouts/pages.
1726
1727
  * An entry is undefined if the layout/page has no component or universal file (i.e. only has a `.server.js` file).
1727
1728
  * Only set in case of `router.resolution === 'server'`.
1728
1729
  */
1729
- nodes?: (string | undefined)[];
1730
+ nodes?: Array<string | undefined>;
1730
1731
  /**
1731
1732
  * CSS files referenced in the entry points of the layouts/pages.
1732
1733
  * An entry is undefined if the layout/page has no component or universal file (i.e. only has a `.server.js` file) or if has no CSS.
1733
1734
  * Only set in case of `router.resolution === 'server'`.
1734
1735
  */
1735
- css?: (string[] | undefined)[];
1736
+ css?: Array<string[] | undefined>;
1736
1737
  /**
1737
1738
  * Contains the client route manifest in a form suitable for the server which is used for server side route resolution.
1738
1739
  * Notably, it contains all routes, regardless of whether they are prerendered or not (those are missing in the optimized server route manifest).
@@ -1742,7 +1743,7 @@ declare module '@sveltejs/kit' {
1742
1743
  stylesheets: string[];
1743
1744
  fonts: string[];
1744
1745
  uses_env_dynamic_public: boolean;
1745
- /** Only set in case of `bundleStrategy === 'inline'` */
1746
+ /** Only set in case of `bundleStrategy === 'inline'`. */
1746
1747
  inline?: {
1747
1748
  script: string;
1748
1749
  style: string | undefined;
@@ -1752,6 +1753,7 @@ declare module '@sveltejs/kit' {
1752
1753
  }
1753
1754
 
1754
1755
  interface ManifestData {
1756
+ /** Static files from `kit.config.files.assets`. */
1755
1757
  assets: Asset[];
1756
1758
  hooks: {
1757
1759
  client: string | null;
@@ -1765,21 +1767,22 @@ declare module '@sveltejs/kit' {
1765
1767
 
1766
1768
  interface PageNode {
1767
1769
  depth: number;
1768
- /** The +page/layout.svelte */
1770
+ /** The `+page/layout.svelte`. */
1769
1771
  component?: string; // TODO supply default component if it's missing (bit of an edge case)
1770
- /** The +page/layout.js/.ts */
1772
+ /** The `+page/layout.js/.ts`. */
1771
1773
  universal?: string;
1772
- /** The +page/layout.server.js/ts */
1774
+ /** The `+page/layout.server.js/ts`. */
1773
1775
  server?: string;
1774
1776
  parent_id?: string;
1775
1777
  parent?: PageNode;
1776
- /** Filled with the pages that reference this layout (if this is a layout) */
1778
+ /** Filled with the pages that reference this layout (if this is a layout). */
1777
1779
  child_pages?: PageNode[];
1778
1780
  }
1779
1781
 
1780
1782
  type RecursiveRequired<T> = {
1781
1783
  // Recursive implementation of TypeScript's Required utility type.
1782
1784
  // Will recursively continue until it reaches a primitive or Function
1785
+ // eslint-disable-next-line @typescript-eslint/no-unsafe-function-type
1783
1786
  [K in keyof T]-?: Extract<T[K], Function> extends never // If it does not have a Function type
1784
1787
  ? RecursiveRequired<T[K]> // recursively continue through.
1785
1788
  : T[K]; // Use the exact type for everything else
@@ -1841,7 +1844,7 @@ declare module '@sveltejs/kit' {
1841
1844
 
1842
1845
  interface SSRNode {
1843
1846
  component: SSRComponentLoader;
1844
- /** index into the `nodes` array in the generated `client/app.js` */
1847
+ /** index into the `nodes` array in the generated `client/app.js`. */
1845
1848
  index: number;
1846
1849
  /** external JS files that are loaded on the client. `imports[0]` is the entry point (e.g. `client/nodes/0.js`) */
1847
1850
  imports: string[];
@@ -1849,7 +1852,7 @@ declare module '@sveltejs/kit' {
1849
1852
  stylesheets: string[];
1850
1853
  /** external font files that are loaded on the client */
1851
1854
  fonts: string[];
1852
- /** inlined styles */
1855
+ /** inlined styles. */
1853
1856
  inline_styles?(): MaybePromise<Record<string, string>>;
1854
1857
 
1855
1858
  universal: {
@@ -1873,8 +1876,8 @@ declare module '@sveltejs/kit' {
1873
1876
  entries?: PrerenderEntryGenerator;
1874
1877
  };
1875
1878
 
1876
- universal_id: string;
1877
- server_id: string;
1879
+ universal_id?: string;
1880
+ server_id?: string;
1878
1881
  }
1879
1882
 
1880
1883
  type SSRNodeLoader = () => Promise<SSRNode>;
@@ -2002,6 +2005,23 @@ declare module '@sveltejs/kit' {
2002
2005
  * @param e The object to check.
2003
2006
  * */
2004
2007
  export function isActionFailure(e: unknown): e is ActionFailure;
2008
+ /**
2009
+ * Strips possible SvelteKit-internal suffixes and trailing slashes from the URL pathname.
2010
+ * Returns the normalized URL as well as a method for adding the potential suffix back
2011
+ * based on a new pathname (possibly including search) or URL.
2012
+ * ```js
2013
+ * import { normalizeUrl } from '@sveltejs/kit';
2014
+ *
2015
+ * const { url, denormalize } = normalizeUrl('/blog/post/__data.json');
2016
+ * console.log(url.pathname); // /blog/post
2017
+ * console.log(denormalize('/blog/post/a')); // /blog/post/a/__data.json
2018
+ * ```
2019
+ * */
2020
+ export function normalizeUrl(url: URL | string): {
2021
+ url: URL;
2022
+ wasNormalized: boolean;
2023
+ denormalize: (url?: string | URL) => URL;
2024
+ };
2005
2025
  export type LessThan<TNumber extends number, TArray extends any[] = []> = TNumber extends TArray["length"] ? TArray[number] : LessThan<TNumber, [...TArray, TArray["length"]]>;
2006
2026
  export type NumericRange<TStart extends number, TEnd extends number> = Exclude<TEnd | LessThan<TEnd>, LessThan<TStart>>;
2007
2027
  export const VERSION: string;
@@ -88,6 +88,7 @@
88
88
  "json",
89
89
  "text",
90
90
  "isActionFailure",
91
+ "normalizeUrl",
91
92
  "VERSION",
92
93
  "sequence",
93
94
  "getRequest",
@@ -160,6 +161,6 @@
160
161
  null,
161
162
  null
162
163
  ],
163
- "mappings": "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",
164
+ "mappings": "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",
164
165
  "ignoreList": []
165
166
  }