@sveltejs/kit 1.0.0-next.20 → 1.0.0-next.200

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 (77) hide show
  1. package/README.md +12 -9
  2. package/assets/components/error.svelte +19 -3
  3. package/assets/runtime/app/env.js +20 -0
  4. package/assets/runtime/app/navigation.js +45 -13
  5. package/assets/runtime/app/paths.js +1 -2
  6. package/assets/runtime/app/stores.js +15 -9
  7. package/assets/runtime/chunks/utils.js +13 -0
  8. package/assets/runtime/env.js +8 -0
  9. package/assets/runtime/internal/singletons.js +5 -11
  10. package/assets/runtime/internal/start.js +979 -351
  11. package/assets/runtime/paths.js +13 -0
  12. package/dist/chunks/cert.js +29254 -0
  13. package/dist/chunks/constants.js +8 -0
  14. package/dist/chunks/error.js +21 -0
  15. package/dist/chunks/index.js +4745 -0
  16. package/dist/chunks/index2.js +700 -0
  17. package/dist/chunks/index3.js +1060 -0
  18. package/dist/chunks/index4.js +398 -0
  19. package/dist/chunks/index5.js +413 -0
  20. package/dist/chunks/index6.js +15574 -0
  21. package/dist/{standard.js → chunks/standard.js} +16 -18
  22. package/dist/chunks/url.js +59 -0
  23. package/dist/cli.js +947 -67
  24. package/dist/hooks.js +28 -0
  25. package/dist/install-fetch.js +6070 -0
  26. package/dist/node.js +51 -0
  27. package/dist/ssr.js +1771 -0
  28. package/package.json +89 -54
  29. package/svelte-kit.js +2 -0
  30. package/types/ambient-modules.d.ts +173 -0
  31. package/types/app.d.ts +21 -0
  32. package/types/config.d.ts +96 -0
  33. package/types/endpoint.d.ts +18 -0
  34. package/types/helper.d.ts +41 -0
  35. package/types/hooks.d.ts +36 -0
  36. package/types/index.d.ts +17 -0
  37. package/types/internal.d.ts +219 -0
  38. package/types/page.d.ts +77 -0
  39. package/CHANGELOG.md +0 -276
  40. package/assets/runtime/app/navigation.js.map +0 -1
  41. package/assets/runtime/app/paths.js.map +0 -1
  42. package/assets/runtime/app/stores.js.map +0 -1
  43. package/assets/runtime/internal/singletons.js.map +0 -1
  44. package/assets/runtime/internal/start.js.map +0 -1
  45. package/assets/runtime/utils-85ebcc60.js +0 -18
  46. package/assets/runtime/utils-85ebcc60.js.map +0 -1
  47. package/dist/api.js +0 -44
  48. package/dist/api.js.map +0 -1
  49. package/dist/build.js +0 -246
  50. package/dist/build.js.map +0 -1
  51. package/dist/cli.js.map +0 -1
  52. package/dist/colors.js +0 -37
  53. package/dist/colors.js.map +0 -1
  54. package/dist/create_app.js +0 -578
  55. package/dist/create_app.js.map +0 -1
  56. package/dist/index.js +0 -12042
  57. package/dist/index.js.map +0 -1
  58. package/dist/index2.js +0 -544
  59. package/dist/index2.js.map +0 -1
  60. package/dist/index3.js +0 -71
  61. package/dist/index3.js.map +0 -1
  62. package/dist/index4.js +0 -466
  63. package/dist/index4.js.map +0 -1
  64. package/dist/index5.js +0 -725
  65. package/dist/index5.js.map +0 -1
  66. package/dist/index6.js +0 -713
  67. package/dist/index6.js.map +0 -1
  68. package/dist/logging.js +0 -43
  69. package/dist/logging.js.map +0 -1
  70. package/dist/package.js +0 -432
  71. package/dist/package.js.map +0 -1
  72. package/dist/renderer.js +0 -2391
  73. package/dist/renderer.js.map +0 -1
  74. package/dist/standard.js.map +0 -1
  75. package/dist/utils.js +0 -54
  76. package/dist/utils.js.map +0 -1
  77. package/svelte-kit +0 -3
@@ -0,0 +1,1060 @@
1
+ import fs__default from 'fs';
2
+ import path__default from 'path';
3
+ import { svelte } from '@sveltejs/vite-plugin-svelte';
4
+ import require$$0 from 'os';
5
+ import vite from 'vite';
6
+ import { r as rimraf, a as resolve_entry, b as posixify, c as copy_assets, p as print_config_conflicts } from '../cli.js';
7
+ import { c as create_manifest_data, a as create_app, d as deep_merge } from './index2.js';
8
+ import { S as SVELTE_KIT } from './constants.js';
9
+ import 'sade';
10
+ import 'child_process';
11
+ import 'net';
12
+ import 'url';
13
+ import './error.js';
14
+ import './standard.js';
15
+
16
+ const isWin$1 = process.platform === 'win32';
17
+ const SEP = isWin$1 ? `\\\\+` : `\\/`;
18
+ const SEP_ESC = isWin$1 ? `\\\\` : `/`;
19
+ const GLOBSTAR = `((?:[^/]*(?:/|$))*)`;
20
+ const WILDCARD = `([^/]*)`;
21
+ const GLOBSTAR_SEGMENT = `((?:[^${SEP_ESC}]*(?:${SEP_ESC}|$))*)`;
22
+ const WILDCARD_SEGMENT = `([^${SEP_ESC}]*)`;
23
+
24
+ /**
25
+ * Convert any glob pattern to a JavaScript Regexp object
26
+ * @param {String} glob Glob pattern to convert
27
+ * @param {Object} opts Configuration object
28
+ * @param {Boolean} [opts.extended=false] Support advanced ext globbing
29
+ * @param {Boolean} [opts.globstar=false] Support globstar
30
+ * @param {Boolean} [opts.strict=true] be laissez faire about mutiple slashes
31
+ * @param {Boolean} [opts.filepath=''] Parse as filepath for extra path related features
32
+ * @param {String} [opts.flags=''] RegExp globs
33
+ * @returns {Object} converted object with string, segments and RegExp object
34
+ */
35
+ function globrex$1(glob, {extended = false, globstar = false, strict = false, filepath = false, flags = ''} = {}) {
36
+ let regex = '';
37
+ let segment = '';
38
+ let path = { regex: '', segments: [] };
39
+
40
+ // If we are doing extended matching, this boolean is true when we are inside
41
+ // a group (eg {*.html,*.js}), and false otherwise.
42
+ let inGroup = false;
43
+ let inRange = false;
44
+
45
+ // extglob stack. Keep track of scope
46
+ const ext = [];
47
+
48
+ // Helper function to build string and segments
49
+ function add(str, {split, last, only}={}) {
50
+ if (only !== 'path') regex += str;
51
+ if (filepath && only !== 'regex') {
52
+ path.regex += (str === '\\/' ? SEP : str);
53
+ if (split) {
54
+ if (last) segment += str;
55
+ if (segment !== '') {
56
+ if (!flags.includes('g')) segment = `^${segment}$`; // change it 'includes'
57
+ path.segments.push(new RegExp(segment, flags));
58
+ }
59
+ segment = '';
60
+ } else {
61
+ segment += str;
62
+ }
63
+ }
64
+ }
65
+
66
+ let c, n;
67
+ for (let i = 0; i < glob.length; i++) {
68
+ c = glob[i];
69
+ n = glob[i + 1];
70
+
71
+ if (['\\', '$', '^', '.', '='].includes(c)) {
72
+ add(`\\${c}`);
73
+ continue;
74
+ }
75
+
76
+ if (c === '/') {
77
+ add(`\\${c}`, {split: true});
78
+ if (n === '/' && !strict) regex += '?';
79
+ continue;
80
+ }
81
+
82
+ if (c === '(') {
83
+ if (ext.length) {
84
+ add(c);
85
+ continue;
86
+ }
87
+ add(`\\${c}`);
88
+ continue;
89
+ }
90
+
91
+ if (c === ')') {
92
+ if (ext.length) {
93
+ add(c);
94
+ let type = ext.pop();
95
+ if (type === '@') {
96
+ add('{1}');
97
+ } else if (type === '!') {
98
+ add('([^\/]*)');
99
+ } else {
100
+ add(type);
101
+ }
102
+ continue;
103
+ }
104
+ add(`\\${c}`);
105
+ continue;
106
+ }
107
+
108
+ if (c === '|') {
109
+ if (ext.length) {
110
+ add(c);
111
+ continue;
112
+ }
113
+ add(`\\${c}`);
114
+ continue;
115
+ }
116
+
117
+ if (c === '+') {
118
+ if (n === '(' && extended) {
119
+ ext.push(c);
120
+ continue;
121
+ }
122
+ add(`\\${c}`);
123
+ continue;
124
+ }
125
+
126
+ if (c === '@' && extended) {
127
+ if (n === '(') {
128
+ ext.push(c);
129
+ continue;
130
+ }
131
+ }
132
+
133
+ if (c === '!') {
134
+ if (extended) {
135
+ if (inRange) {
136
+ add('^');
137
+ continue
138
+ }
139
+ if (n === '(') {
140
+ ext.push(c);
141
+ add('(?!');
142
+ i++;
143
+ continue;
144
+ }
145
+ add(`\\${c}`);
146
+ continue;
147
+ }
148
+ add(`\\${c}`);
149
+ continue;
150
+ }
151
+
152
+ if (c === '?') {
153
+ if (extended) {
154
+ if (n === '(') {
155
+ ext.push(c);
156
+ } else {
157
+ add('.');
158
+ }
159
+ continue;
160
+ }
161
+ add(`\\${c}`);
162
+ continue;
163
+ }
164
+
165
+ if (c === '[') {
166
+ if (inRange && n === ':') {
167
+ i++; // skip [
168
+ let value = '';
169
+ while(glob[++i] !== ':') value += glob[i];
170
+ if (value === 'alnum') add('(\\w|\\d)');
171
+ else if (value === 'space') add('\\s');
172
+ else if (value === 'digit') add('\\d');
173
+ i++; // skip last ]
174
+ continue;
175
+ }
176
+ if (extended) {
177
+ inRange = true;
178
+ add(c);
179
+ continue;
180
+ }
181
+ add(`\\${c}`);
182
+ continue;
183
+ }
184
+
185
+ if (c === ']') {
186
+ if (extended) {
187
+ inRange = false;
188
+ add(c);
189
+ continue;
190
+ }
191
+ add(`\\${c}`);
192
+ continue;
193
+ }
194
+
195
+ if (c === '{') {
196
+ if (extended) {
197
+ inGroup = true;
198
+ add('(');
199
+ continue;
200
+ }
201
+ add(`\\${c}`);
202
+ continue;
203
+ }
204
+
205
+ if (c === '}') {
206
+ if (extended) {
207
+ inGroup = false;
208
+ add(')');
209
+ continue;
210
+ }
211
+ add(`\\${c}`);
212
+ continue;
213
+ }
214
+
215
+ if (c === ',') {
216
+ if (inGroup) {
217
+ add('|');
218
+ continue;
219
+ }
220
+ add(`\\${c}`);
221
+ continue;
222
+ }
223
+
224
+ if (c === '*') {
225
+ if (n === '(' && extended) {
226
+ ext.push(c);
227
+ continue;
228
+ }
229
+ // Move over all consecutive "*"'s.
230
+ // Also store the previous and next characters
231
+ let prevChar = glob[i - 1];
232
+ let starCount = 1;
233
+ while (glob[i + 1] === '*') {
234
+ starCount++;
235
+ i++;
236
+ }
237
+ let nextChar = glob[i + 1];
238
+ if (!globstar) {
239
+ // globstar is disabled, so treat any number of "*" as one
240
+ add('.*');
241
+ } else {
242
+ // globstar is enabled, so determine if this is a globstar segment
243
+ let isGlobstar =
244
+ starCount > 1 && // multiple "*"'s
245
+ (prevChar === '/' || prevChar === undefined) && // from the start of the segment
246
+ (nextChar === '/' || nextChar === undefined); // to the end of the segment
247
+ if (isGlobstar) {
248
+ // it's a globstar, so match zero or more path segments
249
+ add(GLOBSTAR, {only:'regex'});
250
+ add(GLOBSTAR_SEGMENT, {only:'path', last:true, split:true});
251
+ i++; // move over the "/"
252
+ } else {
253
+ // it's not a globstar, so only match one path segment
254
+ add(WILDCARD, {only:'regex'});
255
+ add(WILDCARD_SEGMENT, {only:'path'});
256
+ }
257
+ }
258
+ continue;
259
+ }
260
+
261
+ add(c);
262
+ }
263
+
264
+
265
+ // When regexp 'g' flag is specified don't
266
+ // constrain the regular expression with ^ & $
267
+ if (!flags.includes('g')) {
268
+ regex = `^${regex}$`;
269
+ segment = `^${segment}$`;
270
+ if (filepath) path.regex = `^${path.regex}$`;
271
+ }
272
+
273
+ const result = {regex: new RegExp(regex, flags)};
274
+
275
+ // Push the last segment
276
+ if (filepath) {
277
+ path.segments.push(new RegExp(segment, flags));
278
+ path.regex = new RegExp(path.regex, flags);
279
+ path.globstar = new RegExp(!flags.includes('g') ? `^${GLOBSTAR_SEGMENT}$` : GLOBSTAR_SEGMENT, flags);
280
+ result.path = path;
281
+ }
282
+
283
+ return result;
284
+ }
285
+
286
+ var globrex_1 = globrex$1;
287
+
288
+ const os = require$$0;
289
+ const path = path__default;
290
+ const isWin = os.platform() === 'win32';
291
+
292
+ const CHARS = { '{': '}', '(': ')', '[': ']'};
293
+ const STRICT = /\\(.)|(^!|\*|[\].+)]\?|\[[^\\\]]+\]|\{[^\\}]+\}|\(\?[:!=][^\\)]+\)|\([^|]+\|[^\\)]+\)|(\\).|([@?!+*]\(.*\)))/;
294
+ const RELAXED = /\\(.)|(^!|[*?{}()[\]]|\(\?)/;
295
+
296
+ /**
297
+ * Detect if a string cointains glob
298
+ * @param {String} str Input string
299
+ * @param {Object} [options] Configuration object
300
+ * @param {Boolean} [options.strict=true] Use relaxed regex if true
301
+ * @returns {Boolean} true if string contains glob
302
+ */
303
+ function isglob(str, { strict = true } = {}) {
304
+ if (str === '') return false;
305
+ let match, rgx = strict ? STRICT : RELAXED;
306
+
307
+ while ((match = rgx.exec(str))) {
308
+ if (match[2]) return true;
309
+ let idx = match.index + match[0].length;
310
+
311
+ // if an open bracket/brace/paren is escaped,
312
+ // set the index to the next closing character
313
+ let open = match[1];
314
+ let close = open ? CHARS[open] : null;
315
+ if (open && close) {
316
+ let n = str.indexOf(close, idx);
317
+ if (n !== -1) idx = n + 1;
318
+ }
319
+
320
+ str = str.slice(idx);
321
+ }
322
+ return false;
323
+ }
324
+
325
+
326
+ /**
327
+ * Find the static part of a glob-path,
328
+ * split path and return path part
329
+ * @param {String} str Path/glob string
330
+ * @returns {String} static path section of glob
331
+ */
332
+ function parent(str, { strict = false } = {}) {
333
+ if (isWin && str.includes('/'))
334
+ str = str.split('\\').join('/');
335
+
336
+ // special case for strings ending in enclosure containing path separator
337
+ if (/[\{\[].*[\/]*.*[\}\]]$/.test(str)) str += '/';
338
+
339
+ // preserves full path in case of trailing path separator
340
+ str += 'a';
341
+
342
+ do {str = path.dirname(str);}
343
+ while (isglob(str, {strict}) || /(^|[^\\])([\{\[]|\([^\)]+$)/.test(str));
344
+
345
+ // remove escape chars and return result
346
+ return str.replace(/\\([\*\?\|\[\]\(\)\{\}])/g, '$1');
347
+ }
348
+
349
+ /**
350
+ * Parse a glob path, and split it by static/glob part
351
+ * @param {String} pattern String path
352
+ * @param {Object} [opts] Options
353
+ * @param {Object} [opts.strict=false] Use strict parsing
354
+ * @returns {Object} object with parsed path
355
+ */
356
+ function globalyzer$1(pattern, opts = {}) {
357
+ let base = parent(pattern, opts);
358
+ let isGlob = isglob(pattern, opts);
359
+ let glob;
360
+
361
+ if (base != '.') {
362
+ glob = pattern.substr(base.length);
363
+ if (glob.startsWith('/')) glob = glob.substr(1);
364
+ } else {
365
+ glob = pattern;
366
+ }
367
+
368
+ if (!isGlob) {
369
+ base = path.dirname(pattern);
370
+ glob = base !== '.' ? pattern.substr(base.length) : pattern;
371
+ }
372
+
373
+ if (glob.startsWith('./')) glob = glob.substr(2);
374
+ if (glob.startsWith('/')) glob = glob.substr(1);
375
+
376
+ return { base, glob, isGlob };
377
+ }
378
+
379
+
380
+ var src = globalyzer$1;
381
+
382
+ const fs = fs__default;
383
+ const globrex = globrex_1;
384
+ const globalyzer = src;
385
+ const { join, resolve, relative } = path__default;
386
+ const isHidden = /(^|[\\\/])\.[^\\\/\.]/g;
387
+
388
+ let CACHE = {};
389
+
390
+ function walk(output, prefix, lexer, opts, dirname='', level=0) {
391
+ const rgx = lexer.segments[level];
392
+ const dir = resolve(opts.cwd, prefix, dirname);
393
+ const files = fs.readdirSync(dir);
394
+ const { dot, filesOnly } = opts;
395
+
396
+ let i=0, len=files.length, file;
397
+ let fullpath, relpath, stats, isMatch;
398
+
399
+ for (; i < len; i++) {
400
+ fullpath = join(dir, file=files[i]);
401
+ relpath = dirname ? join(dirname, file) : file;
402
+ if (!dot && isHidden.test(relpath)) continue;
403
+ isMatch = lexer.regex.test(relpath);
404
+
405
+ if ((stats=CACHE[relpath]) === void 0) {
406
+ CACHE[relpath] = stats = fs.lstatSync(fullpath);
407
+ }
408
+
409
+ if (!stats.isDirectory()) {
410
+ isMatch && output.push(relative(opts.cwd, fullpath));
411
+ continue;
412
+ }
413
+
414
+ if (rgx && !rgx.test(file)) continue;
415
+ !filesOnly && isMatch && output.push(join(prefix, relpath));
416
+
417
+ walk(output, prefix, lexer, opts, relpath, rgx && rgx.toString() !== lexer.globstar && level + 1);
418
+ }
419
+ }
420
+
421
+ /**
422
+ * Find files using bash-like globbing.
423
+ * All paths are normalized compared to node-glob.
424
+ * @param {String} str Glob string
425
+ * @param {String} [options.cwd='.'] Current working directory
426
+ * @param {Boolean} [options.dot=false] Include dotfile matches
427
+ * @param {Boolean} [options.absolute=false] Return absolute paths
428
+ * @param {Boolean} [options.filesOnly=false] Do not include folders if true
429
+ * @param {Boolean} [options.flush=false] Reset cache object
430
+ * @returns {Array} array containing matching files
431
+ */
432
+ var sync = function (str, opts={}) {
433
+ if (!str) return [];
434
+
435
+ let glob = globalyzer(str);
436
+
437
+ opts.cwd = opts.cwd || '.';
438
+
439
+ if (!glob.isGlob) {
440
+ try {
441
+ let resolved = resolve(opts.cwd, str);
442
+ let dirent = fs.statSync(resolved);
443
+ if (opts.filesOnly && !dirent.isFile()) return [];
444
+
445
+ return opts.absolute ? [resolved] : [str];
446
+ } catch (err) {
447
+ if (err.code != 'ENOENT') throw err;
448
+
449
+ return [];
450
+ }
451
+ }
452
+
453
+ if (opts.flush) CACHE = {};
454
+
455
+ let matches = [];
456
+ const { path } = globrex(glob.glob, { filepath:true, globstar:true, extended:true });
457
+
458
+ path.globstar = path.globstar.toString();
459
+ walk(matches, glob.base, path, opts, '.', 0);
460
+
461
+ return opts.absolute ? matches.map(x => resolve(opts.cwd, x)) : matches;
462
+ };
463
+
464
+ var glob = sync;
465
+
466
+ /** @param {any} value */
467
+ const s = (value) => JSON.stringify(value);
468
+
469
+ /**
470
+ * @param {import('types/config').ValidatedConfig} config
471
+ * @param {{
472
+ * cwd?: string;
473
+ * runtime?: string;
474
+ * }} [opts]
475
+ * @returns {Promise<import('types/internal').BuildData>}
476
+ */
477
+ async function build(config, { cwd = process.cwd(), runtime = '@sveltejs/kit/ssr' } = {}) {
478
+ const build_dir = path__default.resolve(cwd, `${SVELTE_KIT}/build`);
479
+
480
+ rimraf(build_dir);
481
+
482
+ const output_dir = path__default.resolve(cwd, `${SVELTE_KIT}/output`);
483
+
484
+ const options = {
485
+ cwd,
486
+ config,
487
+ build_dir,
488
+ // TODO this is so that Vite's preloading works. Unfortunately, it fails
489
+ // during `svelte-kit preview`, because we use a local asset path. If Vite
490
+ // used relative paths, I _think_ this could get fixed. Issue here:
491
+ // https://github.com/vitejs/vite/issues/2009
492
+ assets_base: `${config.kit.paths.assets || config.kit.paths.base}/${config.kit.appDir}/`,
493
+ manifest: create_manifest_data({
494
+ config,
495
+ output: build_dir,
496
+ cwd
497
+ }),
498
+ output_dir,
499
+ client_entry_file: `${SVELTE_KIT}/build/runtime/internal/start.js`,
500
+ service_worker_entry_file: resolve_entry(config.kit.files.serviceWorker)
501
+ };
502
+
503
+ const client_manifest = await build_client(options);
504
+ await build_server(options, client_manifest, runtime);
505
+
506
+ if (options.service_worker_entry_file) {
507
+ if (config.kit.paths.assets) {
508
+ throw new Error('Cannot use service worker alongside config.kit.paths.assets');
509
+ }
510
+
511
+ await build_service_worker(options, client_manifest);
512
+ }
513
+
514
+ const client = glob('**', { cwd: `${output_dir}/client`, filesOnly: true }).map(posixify);
515
+ const server = glob('**', { cwd: `${output_dir}/server`, filesOnly: true }).map(posixify);
516
+
517
+ return {
518
+ client,
519
+ server,
520
+ static: options.manifest.assets.map((asset) => posixify(asset.file)),
521
+ entries: options.manifest.routes
522
+ .map((route) => (route.type === 'page' ? route.path : ''))
523
+ .filter(Boolean)
524
+ };
525
+ }
526
+
527
+ /**
528
+ * @param {{
529
+ * cwd: string;
530
+ * assets_base: string;
531
+ * config: import('types/config').ValidatedConfig
532
+ * manifest: import('types/internal').ManifestData
533
+ * build_dir: string;
534
+ * output_dir: string;
535
+ * client_entry_file: string;
536
+ * service_worker_entry_file: string | null;
537
+ * }} options
538
+ */
539
+ async function build_client({
540
+ cwd,
541
+ assets_base,
542
+ config,
543
+ manifest,
544
+ build_dir,
545
+ output_dir,
546
+ client_entry_file
547
+ }) {
548
+ create_app({
549
+ manifest_data: manifest,
550
+ output: build_dir,
551
+ cwd
552
+ });
553
+
554
+ copy_assets(build_dir);
555
+
556
+ process.env.VITE_SVELTEKIT_AMP = config.kit.amp ? 'true' : '';
557
+
558
+ const client_out_dir = `${output_dir}/client/${config.kit.appDir}`;
559
+
560
+ /** @type {Record<string, string>} */
561
+ const input = {
562
+ start: path__default.resolve(cwd, client_entry_file)
563
+ };
564
+
565
+ // This step is optional — Vite/Rollup will create the necessary chunks
566
+ // for everything regardless — but it means that entry chunks reflect
567
+ // their location in the source code, which is helpful for debugging
568
+ manifest.components.forEach((file) => {
569
+ const resolved = path__default.resolve(cwd, file);
570
+ const relative = path__default.relative(config.kit.files.routes, resolved);
571
+
572
+ const name = relative.startsWith('..')
573
+ ? path__default.basename(file)
574
+ : posixify(path__default.join('pages', relative));
575
+ input[name] = resolved;
576
+ });
577
+
578
+ /** @type {import('vite').UserConfig} */
579
+ const vite_config = config.kit.vite();
580
+
581
+ const default_config = {
582
+ server: {
583
+ fs: {
584
+ strict: true
585
+ }
586
+ }
587
+ };
588
+
589
+ // don't warn on overriding defaults
590
+ const [modified_vite_config] = deep_merge(default_config, vite_config);
591
+
592
+ /** @type {[any, string[]]} */
593
+ const [merged_config, conflicts] = deep_merge(modified_vite_config, {
594
+ configFile: false,
595
+ root: cwd,
596
+ base: assets_base,
597
+ build: {
598
+ cssCodeSplit: true,
599
+ manifest: true,
600
+ outDir: client_out_dir,
601
+ polyfillDynamicImport: false,
602
+ rollupOptions: {
603
+ input,
604
+ output: {
605
+ entryFileNames: '[name]-[hash].js',
606
+ chunkFileNames: 'chunks/[name]-[hash].js',
607
+ assetFileNames: 'assets/[name]-[hash][extname]'
608
+ },
609
+ preserveEntrySignatures: 'strict'
610
+ }
611
+ },
612
+ resolve: {
613
+ alias: {
614
+ $app: path__default.resolve(`${build_dir}/runtime/app`),
615
+ $lib: config.kit.files.lib
616
+ }
617
+ },
618
+ plugins: [
619
+ svelte({
620
+ extensions: config.extensions,
621
+ emitCss: !config.kit.amp,
622
+ compilerOptions: {
623
+ hydratable: !!config.kit.hydrate
624
+ }
625
+ })
626
+ ]
627
+ });
628
+
629
+ print_config_conflicts(conflicts, 'kit.vite.', 'build_client');
630
+
631
+ await vite.build(merged_config);
632
+
633
+ const client_manifest_file = `${client_out_dir}/manifest.json`;
634
+ /** @type {import('vite').Manifest} */
635
+ const client_manifest = JSON.parse(fs__default.readFileSync(client_manifest_file, 'utf-8'));
636
+ fs__default.renameSync(client_manifest_file, `${output_dir}/manifest.json`); // inspectable but not shipped
637
+
638
+ return client_manifest;
639
+ }
640
+
641
+ /**
642
+ * @param {{
643
+ * cwd: string;
644
+ * assets_base: string;
645
+ * config: import('types/config').ValidatedConfig
646
+ * manifest: import('types/internal').ManifestData
647
+ * build_dir: string;
648
+ * output_dir: string;
649
+ * client_entry_file: string;
650
+ * service_worker_entry_file: string | null;
651
+ * }} options
652
+ * @param {import('vite').Manifest} client_manifest
653
+ * @param {string} runtime
654
+ */
655
+ async function build_server(
656
+ {
657
+ cwd,
658
+ assets_base,
659
+ config,
660
+ manifest,
661
+ build_dir,
662
+ output_dir,
663
+ client_entry_file,
664
+ service_worker_entry_file
665
+ },
666
+ client_manifest,
667
+ runtime
668
+ ) {
669
+ let hooks_file = resolve_entry(config.kit.files.hooks);
670
+ if (!hooks_file || !fs__default.existsSync(hooks_file)) {
671
+ hooks_file = path__default.resolve(cwd, `${SVELTE_KIT}/build/hooks.js`);
672
+ fs__default.writeFileSync(hooks_file, '');
673
+ }
674
+
675
+ const app_file = `${build_dir}/app.js`;
676
+
677
+ /** @type {(file: string) => string} */
678
+ const app_relative = (file) => {
679
+ const relative_file = path__default.relative(build_dir, path__default.resolve(cwd, file));
680
+ return relative_file[0] === '.' ? relative_file : `./${relative_file}`;
681
+ };
682
+
683
+ const prefix = `/${config.kit.appDir}/`;
684
+
685
+ /**
686
+ * @param {string} file
687
+ * @param {Set<string>} js_deps
688
+ * @param {Set<string>} css_deps
689
+ */
690
+ function find_deps(file, js_deps, css_deps) {
691
+ const chunk = client_manifest[file];
692
+
693
+ if (js_deps.has(chunk.file)) return;
694
+ js_deps.add(chunk.file);
695
+
696
+ if (chunk.css) {
697
+ chunk.css.forEach((file) => css_deps.add(file));
698
+ }
699
+
700
+ if (chunk.imports) {
701
+ chunk.imports.forEach((file) => find_deps(file, js_deps, css_deps));
702
+ }
703
+ }
704
+
705
+ /** @type {Record<string, { entry: string, css: string[], js: string[], styles: string[] }>} */
706
+ const metadata_lookup = {};
707
+
708
+ manifest.components.forEach((file) => {
709
+ const js_deps = new Set();
710
+ const css_deps = new Set();
711
+
712
+ find_deps(file, js_deps, css_deps);
713
+
714
+ const js = Array.from(js_deps);
715
+ const css = Array.from(css_deps);
716
+
717
+ const styles = config.kit.amp
718
+ ? Array.from(css_deps).map((url) => {
719
+ const resolved = `${output_dir}/client/${config.kit.appDir}/${url}`;
720
+ return fs__default.readFileSync(resolved, 'utf-8');
721
+ })
722
+ : [];
723
+
724
+ metadata_lookup[file] = {
725
+ entry: client_manifest[file].file,
726
+ css,
727
+ js,
728
+ styles
729
+ };
730
+ });
731
+
732
+ /** @type {Set<string>} */
733
+ const entry_js = new Set();
734
+ /** @type {Set<string>} */
735
+ const entry_css = new Set();
736
+
737
+ find_deps(client_entry_file, entry_js, entry_css);
738
+
739
+ // prettier-ignore
740
+ fs__default.writeFileSync(
741
+ app_file,
742
+ `
743
+ import { respond } from '${runtime}';
744
+ import root from './generated/root.svelte';
745
+ import { set_paths, assets } from './runtime/paths.js';
746
+ import { set_prerendering } from './runtime/env.js';
747
+ import * as user_hooks from ${s(app_relative(hooks_file))};
748
+
749
+ const template = ({ head, body }) => ${s(fs__default.readFileSync(config.kit.files.template, 'utf-8'))
750
+ .replace('%svelte.head%', '" + head + "')
751
+ .replace('%svelte.body%', '" + body + "')};
752
+
753
+ let options = null;
754
+
755
+ const default_settings = { paths: ${s(config.kit.paths)} };
756
+
757
+ // allow paths to be overridden in svelte-kit preview
758
+ // and in prerendering
759
+ export function init(settings = default_settings) {
760
+ set_paths(settings.paths);
761
+ set_prerendering(settings.prerendering || false);
762
+
763
+ const hooks = get_hooks(user_hooks);
764
+
765
+ options = {
766
+ amp: ${config.kit.amp},
767
+ dev: false,
768
+ entry: {
769
+ file: assets + ${s(prefix + client_manifest[client_entry_file].file)},
770
+ css: [${Array.from(entry_css).map(dep => 'assets + ' + s(prefix + dep))}],
771
+ js: [${Array.from(entry_js).map(dep => 'assets + ' + s(prefix + dep))}]
772
+ },
773
+ fetched: undefined,
774
+ floc: ${config.kit.floc},
775
+ get_component_path: id => assets + ${s(prefix)} + entry_lookup[id],
776
+ get_stack: error => String(error), // for security
777
+ handle_error: (error, request) => {
778
+ hooks.handleError({ error, request });
779
+ error.stack = options.get_stack(error);
780
+ },
781
+ hooks,
782
+ hydrate: ${s(config.kit.hydrate)},
783
+ initiator: undefined,
784
+ load_component,
785
+ manifest,
786
+ paths: settings.paths,
787
+ prerender: ${config.kit.prerender.enabled},
788
+ read: settings.read,
789
+ root,
790
+ service_worker: ${service_worker_entry_file ? "'/service-worker.js'" : 'null'},
791
+ router: ${s(config.kit.router)},
792
+ ssr: ${s(config.kit.ssr)},
793
+ target: ${s(config.kit.target)},
794
+ template,
795
+ trailing_slash: ${s(config.kit.trailingSlash)}
796
+ };
797
+ }
798
+
799
+ // input has already been decoded by decodeURI
800
+ // now handle the rest that decodeURIComponent would do
801
+ const d = s => s
802
+ .replace(/%23/g, '#')
803
+ .replace(/%3[Bb]/g, ';')
804
+ .replace(/%2[Cc]/g, ',')
805
+ .replace(/%2[Ff]/g, '/')
806
+ .replace(/%3[Ff]/g, '?')
807
+ .replace(/%3[Aa]/g, ':')
808
+ .replace(/%40/g, '@')
809
+ .replace(/%26/g, '&')
810
+ .replace(/%3[Dd]/g, '=')
811
+ .replace(/%2[Bb]/g, '+')
812
+ .replace(/%24/g, '$');
813
+
814
+ const empty = () => ({});
815
+
816
+ const manifest = {
817
+ assets: ${s(manifest.assets)},
818
+ layout: ${s(manifest.layout)},
819
+ error: ${s(manifest.error)},
820
+ routes: [
821
+ ${manifest.routes
822
+ .map((route) => {
823
+ if (route.type === 'page') {
824
+ const params = get_params(route.params);
825
+
826
+ return `{
827
+ type: 'page',
828
+ pattern: ${route.pattern},
829
+ params: ${params},
830
+ a: [${route.a.map(file => file && s(file)).join(', ')}],
831
+ b: [${route.b.map(file => file && s(file)).join(', ')}]
832
+ }`;
833
+ } else {
834
+ const params = get_params(route.params);
835
+ const load = `() => import(${s(app_relative(route.file))})`;
836
+
837
+ return `{
838
+ type: 'endpoint',
839
+ pattern: ${route.pattern},
840
+ params: ${params},
841
+ load: ${load}
842
+ }`;
843
+ }
844
+ })
845
+ .join(',\n\t\t\t\t\t')}
846
+ ]
847
+ };
848
+
849
+ // this looks redundant, but the indirection allows us to access
850
+ // named imports without triggering Rollup's missing import detection
851
+ const get_hooks = hooks => ({
852
+ getSession: hooks.getSession || (() => ({})),
853
+ handle: hooks.handle || (({ request, resolve }) => resolve(request)),
854
+ handleError: hooks.handleError || (({ error }) => console.error(error.stack)),
855
+ externalFetch: hooks.externalFetch || fetch
856
+ });
857
+
858
+ const module_lookup = {
859
+ ${manifest.components.map(file => `${s(file)}: () => import(${s(app_relative(file))})`)}
860
+ };
861
+
862
+ const metadata_lookup = ${s(metadata_lookup)};
863
+
864
+ async function load_component(file) {
865
+ const { entry, css, js, styles } = metadata_lookup[file];
866
+ return {
867
+ module: await module_lookup[file](),
868
+ entry: assets + ${s(prefix)} + entry,
869
+ css: css.map(dep => assets + ${s(prefix)} + dep),
870
+ js: js.map(dep => assets + ${s(prefix)} + dep),
871
+ styles
872
+ };
873
+ }
874
+
875
+ export function render(request, {
876
+ prerender
877
+ } = {}) {
878
+ const host = ${config.kit.host ? s(config.kit.host) : `request.headers[${s(config.kit.hostHeader || 'host')}]`};
879
+ return respond({ ...request, host }, options, { prerender });
880
+ }
881
+ `
882
+ .replace(/^\t{3}/gm, '')
883
+ .trim()
884
+ );
885
+
886
+ /** @type {import('vite').UserConfig} */
887
+ const vite_config = config.kit.vite();
888
+
889
+ const default_config = {
890
+ build: {
891
+ target: 'es2020'
892
+ },
893
+ server: {
894
+ fs: {
895
+ strict: true
896
+ }
897
+ }
898
+ };
899
+
900
+ // don't warn on overriding defaults
901
+ const [modified_vite_config] = deep_merge(default_config, vite_config);
902
+
903
+ /** @type {[any, string[]]} */
904
+ const [merged_config, conflicts] = deep_merge(modified_vite_config, {
905
+ configFile: false,
906
+ root: cwd,
907
+ base: assets_base,
908
+ build: {
909
+ ssr: true,
910
+ outDir: `${output_dir}/server`,
911
+ polyfillDynamicImport: false,
912
+ rollupOptions: {
913
+ input: {
914
+ app: app_file
915
+ },
916
+ output: {
917
+ format: 'esm',
918
+ entryFileNames: '[name].js',
919
+ chunkFileNames: 'chunks/[name]-[hash].js',
920
+ assetFileNames: 'assets/[name]-[hash][extname]'
921
+ },
922
+ preserveEntrySignatures: 'strict'
923
+ }
924
+ },
925
+ plugins: [
926
+ svelte({
927
+ extensions: config.extensions,
928
+ compilerOptions: {
929
+ hydratable: !!config.kit.hydrate
930
+ }
931
+ })
932
+ ],
933
+ resolve: {
934
+ alias: {
935
+ $app: path__default.resolve(`${build_dir}/runtime/app`),
936
+ $lib: config.kit.files.lib
937
+ }
938
+ }
939
+ });
940
+
941
+ print_config_conflicts(conflicts, 'kit.vite.', 'build_server');
942
+
943
+ await vite.build(merged_config);
944
+ }
945
+
946
+ /**
947
+ * @param {{
948
+ * cwd: string;
949
+ * assets_base: string;
950
+ * config: import('types/config').ValidatedConfig
951
+ * manifest: import('types/internal').ManifestData
952
+ * build_dir: string;
953
+ * output_dir: string;
954
+ * client_entry_file: string;
955
+ * service_worker_entry_file: string | null;
956
+ * }} options
957
+ * @param {import('vite').Manifest} client_manifest
958
+ */
959
+ async function build_service_worker(
960
+ { cwd, assets_base, config, manifest, build_dir, output_dir, service_worker_entry_file },
961
+ client_manifest
962
+ ) {
963
+ // TODO add any assets referenced in template .html file, e.g. favicon?
964
+ const app_files = new Set();
965
+ for (const key in client_manifest) {
966
+ const { file, css } = client_manifest[key];
967
+ app_files.add(file);
968
+ if (css) {
969
+ css.forEach((file) => {
970
+ app_files.add(file);
971
+ });
972
+ }
973
+ }
974
+
975
+ fs__default.writeFileSync(
976
+ `${build_dir}/runtime/service-worker.js`,
977
+ `
978
+ export const timestamp = ${Date.now()};
979
+
980
+ export const build = [
981
+ ${Array.from(app_files)
982
+ .map((file) => `${s(`${config.kit.paths.base}/${config.kit.appDir}/${file}`)}`)
983
+ .join(',\n\t\t\t\t')}
984
+ ];
985
+
986
+ export const files = [
987
+ ${manifest.assets
988
+ .map((asset) => `${s(`${config.kit.paths.base}/${asset.file}`)}`)
989
+ .join(',\n\t\t\t\t')}
990
+ ];
991
+ `
992
+ .replace(/^\t{3}/gm, '')
993
+ .trim()
994
+ );
995
+
996
+ /** @type {import('vite').UserConfig} */
997
+ const vite_config = config.kit.vite();
998
+
999
+ const default_config = {
1000
+ server: {
1001
+ fs: {
1002
+ strict: true
1003
+ }
1004
+ }
1005
+ };
1006
+
1007
+ // don't warn on overriding defaults
1008
+ const [modified_vite_config] = deep_merge(default_config, vite_config);
1009
+
1010
+ /** @type {[any, string[]]} */
1011
+ const [merged_config, conflicts] = deep_merge(modified_vite_config, {
1012
+ configFile: false,
1013
+ root: cwd,
1014
+ base: assets_base,
1015
+ build: {
1016
+ lib: {
1017
+ entry: service_worker_entry_file,
1018
+ name: 'app',
1019
+ formats: ['es']
1020
+ },
1021
+ rollupOptions: {
1022
+ output: {
1023
+ entryFileNames: 'service-worker.js'
1024
+ }
1025
+ },
1026
+ outDir: `${output_dir}/client`,
1027
+ emptyOutDir: false
1028
+ },
1029
+ resolve: {
1030
+ alias: {
1031
+ '$service-worker': path__default.resolve(`${build_dir}/runtime/service-worker`),
1032
+ $lib: config.kit.files.lib
1033
+ }
1034
+ }
1035
+ });
1036
+
1037
+ print_config_conflicts(conflicts, 'kit.vite.', 'build_service_worker');
1038
+
1039
+ await vite.build(merged_config);
1040
+ }
1041
+
1042
+ /** @param {string[]} array */
1043
+ function get_params(array) {
1044
+ // given an array of params like `['x', 'y', 'z']` for
1045
+ // src/routes/[x]/[y]/[z]/svelte, create a function
1046
+ // that turns a RexExpMatchArray into ({ x, y, z })
1047
+ return array.length
1048
+ ? '(m) => ({ ' +
1049
+ array
1050
+ .map((param, i) => {
1051
+ return param.startsWith('...')
1052
+ ? `${param.slice(3)}: d(m[${i + 1}] || '')`
1053
+ : `${param}: d(m[${i + 1}])`;
1054
+ })
1055
+ .join(', ') +
1056
+ '})'
1057
+ : 'empty';
1058
+ }
1059
+
1060
+ export { build };