@sveltejs/kit 1.0.0-next.291 → 1.0.0-next.292

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.
@@ -421,7 +421,7 @@ function create_client({ target, session, base, trailing_slash }) {
421
421
  * @param {import('./types').NavigationIntent} intent
422
422
  * @param {string[]} redirect_chain
423
423
  * @param {boolean} no_cache
424
- * @param {{hash?: string, scroll: { x: number, y: number } | null, keepfocus: boolean}} [opts]
424
+ * @param {{hash?: string, scroll: { x: number, y: number } | null, keepfocus: boolean, details: { replaceState: boolean, state: any } | null}} [opts]
425
425
  */
426
426
  async function update(intent, redirect_chain, no_cache, opts) {
427
427
  const current_token = (token = {});
@@ -478,6 +478,13 @@ function create_client({ target, session, base, trailing_slash }) {
478
478
 
479
479
  updating = true;
480
480
 
481
+ if (opts && opts.details) {
482
+ const { details } = opts;
483
+ const change = details.replaceState ? 0 : 1;
484
+ details.state[INDEX_KEY] = current_history_index += change;
485
+ history[details.replaceState ? 'replaceState' : 'pushState'](details.state, '', intent.url);
486
+ }
487
+
481
488
  if (started) {
482
489
  current = navigation_result.state;
483
490
 
@@ -794,7 +801,7 @@ function create_client({ target, session, base, trailing_slash }) {
794
801
  if (cached) return cached;
795
802
  }
796
803
 
797
- const [pattern, a, b, get_params, has_shadow] = route;
804
+ const [pattern, a, b, get_params, shadow_key] = route;
798
805
  const params = get_params
799
806
  ? // the pattern is for the route which we've already matched to this path
800
807
  get_params(/** @type {RegExpExecArray} */ (pattern.exec(path)))
@@ -845,18 +852,23 @@ function create_client({ target, session, base, trailing_slash }) {
845
852
  /** @type {Record<string, any>} */
846
853
  let props = {};
847
854
 
848
- const is_shadow_page = has_shadow && i === a.length - 1;
855
+ const is_shadow_page = shadow_key !== undefined && i === a.length - 1;
849
856
 
850
857
  if (is_shadow_page) {
851
858
  const res = await fetch(
852
859
  `${url.pathname}${url.pathname.endsWith('/') ? '' : '/'}__data.json${url.search}`,
853
860
  {
854
861
  headers: {
855
- 'x-sveltekit-load': 'true'
862
+ 'x-sveltekit-load': /** @type {string} */ (shadow_key)
856
863
  }
857
864
  }
858
865
  );
859
866
 
867
+ if (res.status === 204) {
868
+ // fallthrough
869
+ return;
870
+ }
871
+
860
872
  if (res.ok) {
861
873
  const redirect = res.headers.get('x-sveltekit-location');
862
874
 
@@ -1105,7 +1117,8 @@ function create_client({ target, session, base, trailing_slash }) {
1105
1117
 
1106
1118
  await update(intent, redirect_chain, false, {
1107
1119
  scroll,
1108
- keepfocus
1120
+ keepfocus,
1121
+ details
1109
1122
  });
1110
1123
 
1111
1124
  navigating--;
@@ -1119,12 +1132,6 @@ function create_client({ target, session, base, trailing_slash }) {
1119
1132
 
1120
1133
  stores.navigating.set(null);
1121
1134
  }
1122
-
1123
- if (details) {
1124
- const change = details.replaceState ? 0 : 1;
1125
- details.state[INDEX_KEY] = current_history_index += change;
1126
- history[details.replaceState ? 'replaceState' : 'pushState'](details.state, '', intent.url);
1127
- }
1128
1135
  }
1129
1136
 
1130
1137
  /**
@@ -2184,12 +2184,16 @@ async function respond$1(opts) {
2184
2184
 
2185
2185
  let page_config = get_page_config(leaf, options);
2186
2186
 
2187
- if (!leaf.prerender && state.prerender && !state.prerender.all) {
2188
- // if the page has `export const prerender = true`, continue,
2189
- // otherwise bail out at this point
2190
- return new Response(undefined, {
2191
- status: 204
2192
- });
2187
+ if (state.prerender) {
2188
+ // if the page isn't marked as prerenderable (or is explicitly
2189
+ // marked NOT prerenderable, if `prerender.default` is `true`),
2190
+ // then bail out at this point
2191
+ const should_prerender = leaf.prerender ?? state.prerender.default;
2192
+ if (!should_prerender) {
2193
+ return new Response(undefined, {
2194
+ status: 204
2195
+ });
2196
+ }
2193
2197
  }
2194
2198
 
2195
2199
  /** @type {Array<Loaded>} */
@@ -2637,7 +2641,17 @@ async function respond(request, options, state = {}) {
2637
2641
  event.url = new URL(event.url.origin + normalized + event.url.search);
2638
2642
  }
2639
2643
 
2644
+ // `key` will be set if this request came from a client-side navigation
2645
+ // to a page with a matching endpoint
2646
+ const key = request.headers.get('x-sveltekit-load');
2647
+
2640
2648
  for (const route of options.manifest._.routes) {
2649
+ if (key) {
2650
+ // client is requesting data for a specific endpoint
2651
+ if (route.type !== 'page') continue;
2652
+ if (route.key !== key) continue;
2653
+ }
2654
+
2641
2655
  const match = route.pattern.exec(decoded);
2642
2656
  if (!match) continue;
2643
2657
 
@@ -2650,7 +2664,7 @@ async function respond(request, options, state = {}) {
2650
2664
  response = await render_endpoint(event, await route.shadow());
2651
2665
 
2652
2666
  // loading data for a client-side transition is a special case
2653
- if (request.headers.get('x-sveltekit-load') === 'true') {
2667
+ if (key) {
2654
2668
  if (response) {
2655
2669
  // since redirects are opaque to the browser, we need to repackage
2656
2670
  // 3xx responses as 200s with a custom header
@@ -2667,9 +2681,9 @@ async function respond(request, options, state = {}) {
2667
2681
  }
2668
2682
  }
2669
2683
  } else {
2670
- // TODO ideally, the client wouldn't request this data
2671
- // in the first place (at least in production)
2672
- response = new Response('{}', {
2684
+ // fallthrough
2685
+ response = new Response(undefined, {
2686
+ status: 204,
2673
2687
  headers: {
2674
2688
  'content-type': 'application/json'
2675
2689
  }
@@ -0,0 +1,110 @@
1
+ import fs__default from 'fs';
2
+ import path__default from 'path';
3
+
4
+ /** @param {string} dir */
5
+ function mkdirp(dir) {
6
+ try {
7
+ fs__default.mkdirSync(dir, { recursive: true });
8
+ } catch (/** @type {any} */ e) {
9
+ if (e.code === 'EEXIST') return;
10
+ throw e;
11
+ }
12
+ }
13
+
14
+ /** @param {string} path */
15
+ function rimraf(path) {
16
+ (fs__default.rmSync || fs__default.rmdirSync)(path, { recursive: true, force: true });
17
+ }
18
+
19
+ /**
20
+ * @param {string} source
21
+ * @param {string} target
22
+ * @param {{
23
+ * filter?: (basename: string) => boolean;
24
+ * replace?: Record<string, string>;
25
+ * }} opts
26
+ */
27
+ function copy(source, target, opts = {}) {
28
+ if (!fs__default.existsSync(source)) return [];
29
+
30
+ /** @type {string[]} */
31
+ const files = [];
32
+
33
+ const prefix = posixify(target) + '/';
34
+
35
+ const regex = opts.replace
36
+ ? new RegExp(`\\b(${Object.keys(opts.replace).join('|')})\\b`, 'g')
37
+ : null;
38
+
39
+ /**
40
+ * @param {string} from
41
+ * @param {string} to
42
+ */
43
+ function go(from, to) {
44
+ if (opts.filter && !opts.filter(path__default.basename(from))) return;
45
+
46
+ const stats = fs__default.statSync(from);
47
+
48
+ if (stats.isDirectory()) {
49
+ fs__default.readdirSync(from).forEach((file) => {
50
+ go(path__default.join(from, file), path__default.join(to, file));
51
+ });
52
+ } else {
53
+ mkdirp(path__default.dirname(to));
54
+
55
+ if (opts.replace) {
56
+ const data = fs__default.readFileSync(from, 'utf-8');
57
+ fs__default.writeFileSync(
58
+ to,
59
+ data.replace(
60
+ /** @type {RegExp} */ (regex),
61
+ (match, key) => /** @type {Record<string, string>} */ (opts.replace)[key]
62
+ )
63
+ );
64
+ } else {
65
+ fs__default.copyFileSync(from, to);
66
+ }
67
+
68
+ files.push(to === target ? posixify(path__default.basename(to)) : posixify(to).replace(prefix, ''));
69
+ }
70
+ }
71
+
72
+ go(source, target);
73
+
74
+ return files;
75
+ }
76
+
77
+ /**
78
+ * Get a list of all files in a directory
79
+ * @param {string} cwd - the directory to walk
80
+ * @param {boolean} [dirs] - whether to include directories in the result
81
+ */
82
+ function walk(cwd, dirs = false) {
83
+ /** @type {string[]} */
84
+ const all_files = [];
85
+
86
+ /** @param {string} dir */
87
+ function walk_dir(dir) {
88
+ const files = fs__default.readdirSync(path__default.join(cwd, dir));
89
+
90
+ for (const file of files) {
91
+ const joined = path__default.join(dir, file);
92
+ const stats = fs__default.statSync(path__default.join(cwd, joined));
93
+ if (stats.isDirectory()) {
94
+ if (dirs) all_files.push(joined);
95
+ walk_dir(joined);
96
+ } else {
97
+ all_files.push(joined);
98
+ }
99
+ }
100
+ }
101
+
102
+ return walk_dir(''), all_files;
103
+ }
104
+
105
+ /** @param {string} str */
106
+ function posixify(str) {
107
+ return str.replace(/\\/g, '/');
108
+ }
109
+
110
+ export { copy as c, mkdirp as m, posixify as p, rimraf as r, walk as w };
@@ -1,15 +1,16 @@
1
1
  import path__default from 'path';
2
2
  import { svelte } from '@sveltejs/vite-plugin-svelte';
3
3
  import vite from 'vite';
4
- import { c as create_manifest_data, a as create_app, g as generate_tsconfig, d as deep_merge } from './tsconfig.js';
5
- import { g as get_runtime_path, r as resolve_entry, $, p as posixify, l as load_template, c as coalesce_to_error, a as get_mime_lookup, b as copy_assets, d as get_aliases, e as print_config_conflicts } from '../cli.js';
4
+ import { d as deep_merge } from './object.js';
5
+ import { g as get_runtime_path, r as resolve_entry, $, l as load_template, c as coalesce_to_error, a as get_mime_lookup, b as get_aliases, p as print_config_conflicts } from '../cli.js';
6
6
  import fs__default from 'fs';
7
7
  import { URL } from 'url';
8
8
  import { S as SVELTE_KIT_ASSETS, s as sirv } from './constants.js';
9
9
  import { installFetch } from '../install-fetch.js';
10
+ import { update, init } from './sync.js';
10
11
  import { getRequest, setResponse } from '../node.js';
11
12
  import { sequence } from '../hooks.js';
12
- import './misc.js';
13
+ import { p as posixify } from './filesystem.js';
13
14
  import 'sade';
14
15
  import 'child_process';
15
16
  import 'net';
@@ -21,6 +22,7 @@ import 'node:zlib';
21
22
  import 'node:stream';
22
23
  import 'node:util';
23
24
  import 'node:url';
25
+ import './misc.js';
24
26
  import 'stream';
25
27
 
26
28
  /**
@@ -54,9 +56,7 @@ async function create_plugin(config, cwd) {
54
56
  let manifest;
55
57
 
56
58
  function update_manifest() {
57
- const manifest_data = create_manifest_data({ config, cwd });
58
-
59
- create_app({ config, manifest_data, cwd });
59
+ const { manifest_data } = update(config);
60
60
 
61
61
  manifest = {
62
62
  appDir: config.kit.appDir,
@@ -119,6 +119,7 @@ async function create_plugin(config, cwd) {
119
119
  if (route.type === 'page') {
120
120
  return {
121
121
  type: 'page',
122
+ key: route.key,
122
123
  pattern: route.pattern,
123
124
  params: get_params(route.params),
124
125
  shadow: route.shadow
@@ -416,9 +417,7 @@ function find_deps(node, deps) {
416
417
 
417
418
  /** @param {Options} opts */
418
419
  async function dev({ cwd, port, host, https, config }) {
419
- copy_assets(path__default.join(config.kit.outDir, 'runtime'));
420
-
421
- generate_tsconfig(config);
420
+ init(config);
422
421
 
423
422
  const [vite_config] = deep_merge(
424
423
  {