@sveltejs/kit 1.0.0-next.99 → 1.0.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 (141) hide show
  1. package/README.md +5 -1
  2. package/package.json +91 -77
  3. package/postinstall.js +47 -0
  4. package/src/cli.js +44 -0
  5. package/src/constants.js +5 -0
  6. package/src/core/adapt/builder.js +221 -0
  7. package/src/core/adapt/index.js +31 -0
  8. package/src/core/config/default-error.html +56 -0
  9. package/src/core/config/index.js +100 -0
  10. package/src/core/config/options.js +387 -0
  11. package/src/core/config/types.d.ts +1 -0
  12. package/src/core/env.js +138 -0
  13. package/src/core/generate_manifest/index.js +116 -0
  14. package/src/core/prerender/crawl.js +207 -0
  15. package/src/core/prerender/entities.js +2252 -0
  16. package/src/core/prerender/fallback.js +43 -0
  17. package/src/core/prerender/prerender.js +459 -0
  18. package/src/core/prerender/queue.js +80 -0
  19. package/src/core/sync/create_manifest_data/conflict.js +0 -0
  20. package/src/core/sync/create_manifest_data/index.js +523 -0
  21. package/src/core/sync/create_manifest_data/sort.js +161 -0
  22. package/src/core/sync/create_manifest_data/types.d.ts +37 -0
  23. package/src/core/sync/sync.js +59 -0
  24. package/src/core/sync/utils.js +33 -0
  25. package/src/core/sync/write_ambient.js +58 -0
  26. package/src/core/sync/write_client_manifest.js +107 -0
  27. package/src/core/sync/write_matchers.js +25 -0
  28. package/src/core/sync/write_root.js +91 -0
  29. package/src/core/sync/write_tsconfig.js +195 -0
  30. package/src/core/sync/write_types/index.js +809 -0
  31. package/src/core/utils.js +67 -0
  32. package/src/exports/hooks/index.js +1 -0
  33. package/src/exports/hooks/sequence.js +44 -0
  34. package/src/exports/index.js +55 -0
  35. package/src/exports/node/index.js +172 -0
  36. package/src/exports/node/polyfills.js +28 -0
  37. package/src/exports/vite/build/build_server.js +359 -0
  38. package/src/exports/vite/build/build_service_worker.js +85 -0
  39. package/src/exports/vite/build/utils.js +230 -0
  40. package/src/exports/vite/dev/index.js +597 -0
  41. package/src/exports/vite/graph_analysis/index.js +99 -0
  42. package/src/exports/vite/graph_analysis/types.d.ts +5 -0
  43. package/src/exports/vite/graph_analysis/utils.js +6 -0
  44. package/src/exports/vite/index.js +708 -0
  45. package/src/exports/vite/preview/index.js +194 -0
  46. package/src/exports/vite/types.d.ts +3 -0
  47. package/src/exports/vite/utils.js +184 -0
  48. package/src/runtime/app/env.js +1 -0
  49. package/src/runtime/app/environment.js +13 -0
  50. package/src/runtime/app/forms.js +135 -0
  51. package/src/runtime/app/navigation.js +22 -0
  52. package/src/runtime/app/paths.js +1 -0
  53. package/src/runtime/app/stores.js +57 -0
  54. package/src/runtime/client/ambient.d.ts +30 -0
  55. package/src/runtime/client/client.js +1725 -0
  56. package/src/runtime/client/constants.js +10 -0
  57. package/src/runtime/client/fetcher.js +127 -0
  58. package/src/runtime/client/parse.js +60 -0
  59. package/src/runtime/client/singletons.js +21 -0
  60. package/src/runtime/client/start.js +45 -0
  61. package/src/runtime/client/types.d.ts +86 -0
  62. package/src/runtime/client/utils.js +257 -0
  63. package/src/runtime/components/error.svelte +6 -0
  64. package/{assets → src/runtime}/components/layout.svelte +0 -0
  65. package/src/runtime/control.js +45 -0
  66. package/src/runtime/env/dynamic/private.js +1 -0
  67. package/src/runtime/env/dynamic/public.js +1 -0
  68. package/src/runtime/env-private.js +6 -0
  69. package/src/runtime/env-public.js +6 -0
  70. package/src/runtime/env.js +12 -0
  71. package/src/runtime/hash.js +20 -0
  72. package/src/runtime/paths.js +11 -0
  73. package/src/runtime/server/cookie.js +228 -0
  74. package/src/runtime/server/data/index.js +158 -0
  75. package/src/runtime/server/endpoint.js +86 -0
  76. package/src/runtime/server/fetch.js +175 -0
  77. package/src/runtime/server/index.js +405 -0
  78. package/src/runtime/server/page/actions.js +267 -0
  79. package/src/runtime/server/page/crypto.js +239 -0
  80. package/src/runtime/server/page/csp.js +250 -0
  81. package/src/runtime/server/page/index.js +326 -0
  82. package/src/runtime/server/page/load_data.js +270 -0
  83. package/src/runtime/server/page/render.js +393 -0
  84. package/src/runtime/server/page/respond_with_error.js +103 -0
  85. package/src/runtime/server/page/serialize_data.js +87 -0
  86. package/src/runtime/server/page/types.d.ts +35 -0
  87. package/src/runtime/server/utils.js +179 -0
  88. package/src/utils/array.js +9 -0
  89. package/src/utils/error.js +22 -0
  90. package/src/utils/escape.js +46 -0
  91. package/src/utils/exports.js +54 -0
  92. package/src/utils/filesystem.js +178 -0
  93. package/src/utils/functions.js +16 -0
  94. package/src/utils/http.js +72 -0
  95. package/src/utils/misc.js +1 -0
  96. package/src/utils/promises.js +17 -0
  97. package/src/utils/routing.js +201 -0
  98. package/src/utils/unit_test.js +11 -0
  99. package/src/utils/url.js +161 -0
  100. package/svelte-kit.js +1 -1
  101. package/types/ambient.d.ts +451 -0
  102. package/types/index.d.ts +1168 -5
  103. package/types/internal.d.ts +348 -159
  104. package/types/private.d.ts +237 -0
  105. package/types/synthetic/$env+dynamic+private.md +10 -0
  106. package/types/synthetic/$env+dynamic+public.md +8 -0
  107. package/types/synthetic/$env+static+private.md +19 -0
  108. package/types/synthetic/$env+static+public.md +7 -0
  109. package/types/synthetic/$lib.md +5 -0
  110. package/CHANGELOG.md +0 -825
  111. package/assets/components/error.svelte +0 -21
  112. package/assets/runtime/app/env.js +0 -16
  113. package/assets/runtime/app/navigation.js +0 -53
  114. package/assets/runtime/app/paths.js +0 -1
  115. package/assets/runtime/app/stores.js +0 -87
  116. package/assets/runtime/chunks/utils.js +0 -13
  117. package/assets/runtime/env.js +0 -8
  118. package/assets/runtime/internal/singletons.js +0 -20
  119. package/assets/runtime/internal/start.js +0 -1061
  120. package/assets/runtime/paths.js +0 -12
  121. package/dist/chunks/_commonjsHelpers.js +0 -8
  122. package/dist/chunks/cert.js +0 -29079
  123. package/dist/chunks/constants.js +0 -3
  124. package/dist/chunks/index.js +0 -3532
  125. package/dist/chunks/index2.js +0 -583
  126. package/dist/chunks/index3.js +0 -31
  127. package/dist/chunks/index4.js +0 -1004
  128. package/dist/chunks/index5.js +0 -327
  129. package/dist/chunks/index6.js +0 -325
  130. package/dist/chunks/standard.js +0 -99
  131. package/dist/chunks/utils.js +0 -149
  132. package/dist/cli.js +0 -711
  133. package/dist/http.js +0 -66
  134. package/dist/install-fetch.js +0 -1699
  135. package/dist/ssr.js +0 -1523
  136. package/types/ambient-modules.d.ts +0 -115
  137. package/types/config.d.ts +0 -101
  138. package/types/endpoint.d.ts +0 -23
  139. package/types/helper.d.ts +0 -19
  140. package/types/hooks.d.ts +0 -21
  141. package/types/page.d.ts +0 -30
@@ -0,0 +1,359 @@
1
+ import fs from 'fs';
2
+ import path from 'path';
3
+ import { mergeConfig } from 'vite';
4
+ import { mkdirp, posixify, resolve_entry } from '../../../utils/filesystem.js';
5
+ import { get_vite_config } from '../utils.js';
6
+ import { load_error_page, load_template } from '../../../core/config/index.js';
7
+ import { runtime_directory } from '../../../core/utils.js';
8
+ import {
9
+ create_build,
10
+ find_deps,
11
+ get_default_build_config,
12
+ is_http_method,
13
+ resolve_symlinks
14
+ } from './utils.js';
15
+ import { s } from '../../../utils/misc.js';
16
+
17
+ /**
18
+ * @param {{
19
+ * hooks: string;
20
+ * config: import('types').ValidatedConfig;
21
+ * has_service_worker: boolean;
22
+ * runtime: string;
23
+ * template: string;
24
+ * error_page: string;
25
+ * }} opts
26
+ */
27
+ const server_template = ({ config, hooks, has_service_worker, runtime, template, error_page }) => `
28
+ import root from '__GENERATED__/root.svelte';
29
+ import { respond } from '${runtime}/server/index.js';
30
+ import { set_paths, assets, base } from '${runtime}/paths.js';
31
+ import { set_building, set_version } from '${runtime}/env.js';
32
+ import { set_private_env } from '${runtime}/env-private.js';
33
+ import { set_public_env } from '${runtime}/env-public.js';
34
+
35
+ const app_template = ({ head, body, assets, nonce }) => ${s(template)
36
+ .replace('%sveltekit.head%', '" + head + "')
37
+ .replace('%sveltekit.body%', '" + body + "')
38
+ .replace(/%sveltekit\.assets%/g, '" + assets + "')
39
+ .replace(/%sveltekit\.nonce%/g, '" + nonce + "')};
40
+
41
+ const error_template = ({ status, message }) => ${s(error_page)
42
+ .replace(/%sveltekit\.status%/g, '" + status + "')
43
+ .replace(/%sveltekit\.error\.message%/g, '" + message + "')};
44
+
45
+ let read = null;
46
+
47
+ set_paths(${s(config.kit.paths)});
48
+ set_version(${s(config.kit.version.name)});
49
+
50
+ let default_protocol = 'https';
51
+
52
+ // allow paths to be globally overridden
53
+ // in svelte-kit preview and in prerendering
54
+ export function override(settings) {
55
+ default_protocol = settings.protocol || default_protocol;
56
+ set_paths(settings.paths);
57
+ set_building(settings.building);
58
+ read = settings.read;
59
+ }
60
+
61
+ export class Server {
62
+ constructor(manifest) {
63
+ this.options = {
64
+ csp: ${s(config.kit.csp)},
65
+ csrf: {
66
+ check_origin: ${s(config.kit.csrf.checkOrigin)},
67
+ },
68
+ dev: false,
69
+ embedded: ${config.kit.embedded},
70
+ handle_error: (error, event) => {
71
+ return this.options.hooks.handleError({ error, event }) ?? {
72
+ message: event.route.id != null ? 'Internal Error' : 'Not Found'
73
+ };
74
+ },
75
+ hooks: null,
76
+ manifest,
77
+ paths: { base, assets },
78
+ public_env: {},
79
+ read,
80
+ root,
81
+ service_worker: ${has_service_worker},
82
+ app_template,
83
+ app_template_contains_nonce: ${template.includes('%sveltekit.nonce%')},
84
+ error_template,
85
+ version: ${s(config.kit.version.name)}
86
+ };
87
+ }
88
+
89
+ /**
90
+ * Take care: Some adapters may have to call \`Server.init\` per-request to set env vars,
91
+ * so anything that shouldn't be rerun should be wrapped in an \`if\` block to make sure it hasn't
92
+ * been done already.
93
+ */
94
+ async init({ env }) {
95
+ const entries = Object.entries(env);
96
+
97
+ const prv = Object.fromEntries(entries.filter(([k]) => !k.startsWith('${
98
+ config.kit.env.publicPrefix
99
+ }')));
100
+
101
+ const pub = Object.fromEntries(entries.filter(([k]) => k.startsWith('${
102
+ config.kit.env.publicPrefix
103
+ }')));
104
+
105
+ set_private_env(prv);
106
+ set_public_env(pub);
107
+
108
+ this.options.public_env = pub;
109
+
110
+ if (!this.options.hooks) {
111
+ const module = await import(${s(hooks)});
112
+
113
+ this.options.hooks = {
114
+ handle: module.handle || (({ event, resolve }) => resolve(event)),
115
+ handleError: module.handleError || (({ error }) => console.error(error.stack)),
116
+ handleFetch: module.handleFetch || (({ request, fetch }) => fetch(request))
117
+ };
118
+ }
119
+ }
120
+
121
+ async respond(request, options = {}) {
122
+ if (!(request instanceof Request)) {
123
+ throw new Error('The first argument to server.respond must be a Request object. See https://github.com/sveltejs/kit/pull/3384 for details');
124
+ }
125
+
126
+ return respond(request, this.options, options);
127
+ }
128
+ }
129
+ `;
130
+
131
+ /**
132
+ * @param {{
133
+ * cwd: string;
134
+ * config: import('types').ValidatedConfig;
135
+ * vite_config: import('vite').ResolvedConfig;
136
+ * vite_config_env: import('vite').ConfigEnv;
137
+ * manifest_data: import('types').ManifestData;
138
+ * build_dir: string;
139
+ * output_dir: string;
140
+ * service_worker_entry_file: string | null;
141
+ * }} options
142
+ * @param {{ vite_manifest: import('vite').Manifest, assets: import('rollup').OutputAsset[] }} client
143
+ */
144
+ export async function build_server(options, client) {
145
+ const {
146
+ cwd,
147
+ config,
148
+ vite_config,
149
+ vite_config_env,
150
+ manifest_data,
151
+ build_dir,
152
+ output_dir,
153
+ service_worker_entry_file
154
+ } = options;
155
+
156
+ let hooks_file = resolve_entry(config.kit.files.hooks.server);
157
+
158
+ if (!hooks_file || !fs.existsSync(hooks_file)) {
159
+ hooks_file = path.join(config.kit.outDir, 'build/hooks.js');
160
+ fs.writeFileSync(hooks_file, '');
161
+ }
162
+
163
+ /** @type {Record<string, string>} */
164
+ const input = {
165
+ index: `${build_dir}/index.js`
166
+ };
167
+
168
+ // add entry points for every endpoint...
169
+ manifest_data.routes.forEach((route) => {
170
+ if (route.endpoint) {
171
+ const resolved = path.resolve(cwd, route.endpoint.file);
172
+ const relative = decodeURIComponent(path.relative(config.kit.files.routes, resolved));
173
+ const name = posixify(path.join('entries/endpoints', relative.replace(/\.js$/, '')));
174
+ input[name] = resolved;
175
+ }
176
+ });
177
+
178
+ // ...and every component used by pages...
179
+ manifest_data.nodes.forEach((node) => {
180
+ for (const file of [node.component, node.universal, node.server]) {
181
+ if (file) {
182
+ const resolved = path.resolve(cwd, file);
183
+ const relative = decodeURIComponent(path.relative(config.kit.files.routes, resolved));
184
+
185
+ const name = relative.startsWith('..')
186
+ ? posixify(path.join('entries/fallbacks', path.basename(file)))
187
+ : posixify(path.join('entries/pages', relative.replace(/\.js$/, '')));
188
+ input[name] = resolved;
189
+ }
190
+ }
191
+ });
192
+
193
+ // ...and every matcher
194
+ Object.entries(manifest_data.matchers).forEach(([key, file]) => {
195
+ const name = posixify(path.join('entries/matchers', key));
196
+ input[name] = path.resolve(cwd, file);
197
+ });
198
+
199
+ /** @type {(file: string) => string} */
200
+ const app_relative = (file) => {
201
+ const relative_file = path.relative(build_dir, path.resolve(cwd, file));
202
+ return relative_file[0] === '.' ? relative_file : `./${relative_file}`;
203
+ };
204
+
205
+ fs.writeFileSync(
206
+ input.index,
207
+ server_template({
208
+ config,
209
+ hooks: app_relative(hooks_file),
210
+ has_service_worker: config.kit.serviceWorker.register && !!service_worker_entry_file,
211
+ runtime: posixify(path.relative(build_dir, runtime_directory)),
212
+ template: load_template(cwd, config),
213
+ error_page: load_error_page(config)
214
+ })
215
+ );
216
+
217
+ const merged_config = mergeConfig(
218
+ get_default_build_config({ config, input, ssr: true, outDir: `${output_dir}/server` }),
219
+ await get_vite_config(vite_config, vite_config_env)
220
+ );
221
+
222
+ const { chunks } = await create_build(merged_config);
223
+
224
+ /** @type {import('vite').Manifest} */
225
+ const vite_manifest = JSON.parse(
226
+ fs.readFileSync(`${output_dir}/server/${vite_config.build.manifest}`, 'utf-8')
227
+ );
228
+
229
+ mkdirp(`${output_dir}/server/nodes`);
230
+ mkdirp(`${output_dir}/server/stylesheets`);
231
+
232
+ const stylesheet_lookup = new Map();
233
+
234
+ client.assets.forEach((asset) => {
235
+ if (asset.fileName.endsWith('.css')) {
236
+ if (asset.source.length < config.kit.inlineStyleThreshold) {
237
+ const index = stylesheet_lookup.size;
238
+ const file = `${output_dir}/server/stylesheets/${index}.js`;
239
+
240
+ fs.writeFileSync(file, `// ${asset.fileName}\nexport default ${s(asset.source)};`);
241
+ stylesheet_lookup.set(asset.fileName, index);
242
+ }
243
+ }
244
+ });
245
+
246
+ manifest_data.nodes.forEach((node, i) => {
247
+ /** @type {string[]} */
248
+ const imports = [];
249
+
250
+ // String representation of
251
+ /** @type {import('types').SSRNode} */
252
+ /** @type {string[]} */
253
+ const exports = [`export const index = ${i};`];
254
+
255
+ /** @type {string[]} */
256
+ const imported = [];
257
+
258
+ /** @type {string[]} */
259
+ const stylesheets = [];
260
+
261
+ /** @type {string[]} */
262
+ const fonts = [];
263
+
264
+ if (node.component) {
265
+ const entry = find_deps(client.vite_manifest, node.component, true);
266
+
267
+ imported.push(...entry.imports);
268
+ stylesheets.push(...entry.stylesheets);
269
+ fonts.push(...entry.fonts);
270
+
271
+ exports.push(
272
+ `export const component = async () => (await import('../${
273
+ resolve_symlinks(vite_manifest, node.component).chunk.file
274
+ }')).default;`,
275
+ `export const file = '${entry.file}';` // TODO what is this?
276
+ );
277
+ }
278
+
279
+ if (node.universal) {
280
+ const entry = find_deps(client.vite_manifest, node.universal, true);
281
+
282
+ imported.push(...entry.imports);
283
+ stylesheets.push(...entry.stylesheets);
284
+ fonts.push(...entry.fonts);
285
+
286
+ imports.push(`import * as universal from '../${vite_manifest[node.universal].file}';`);
287
+ exports.push(`export { universal };`);
288
+ }
289
+
290
+ if (node.server) {
291
+ imports.push(`import * as server from '../${vite_manifest[node.server].file}';`);
292
+ exports.push(`export { server };`);
293
+ }
294
+
295
+ exports.push(
296
+ `export const imports = ${s(imported)};`,
297
+ `export const stylesheets = ${s(stylesheets)};`,
298
+ `export const fonts = ${s(fonts)};`
299
+ );
300
+
301
+ /** @type {string[]} */
302
+ const styles = [];
303
+
304
+ stylesheets.forEach((file) => {
305
+ if (stylesheet_lookup.has(file)) {
306
+ const index = stylesheet_lookup.get(file);
307
+ const name = `stylesheet_${index}`;
308
+ imports.push(`import ${name} from '../stylesheets/${index}.js';`);
309
+ styles.push(`\t${s(file)}: ${name}`);
310
+ }
311
+ });
312
+
313
+ if (styles.length > 0) {
314
+ exports.push(`export const inline_styles = () => ({\n${styles.join(',\n')}\n});`);
315
+ }
316
+
317
+ const out = `${output_dir}/server/nodes/${i}.js`;
318
+ fs.writeFileSync(out, `${imports.join('\n')}\n\n${exports.join('\n')}\n`);
319
+ });
320
+
321
+ return {
322
+ chunks,
323
+ vite_manifest,
324
+ methods: get_methods(cwd, chunks, manifest_data)
325
+ };
326
+ }
327
+
328
+ /**
329
+ * @param {string} cwd
330
+ * @param {import('rollup').OutputChunk[]} output
331
+ * @param {import('types').ManifestData} manifest_data
332
+ */
333
+ function get_methods(cwd, output, manifest_data) {
334
+ /** @type {Record<string, string[]>} */
335
+ const lookup = {};
336
+ output.forEach((chunk) => {
337
+ if (!chunk.facadeModuleId) return;
338
+ const id = posixify(path.relative(cwd, chunk.facadeModuleId));
339
+ lookup[id] = chunk.exports;
340
+ });
341
+
342
+ /** @type {Record<string, import('types').HttpMethod[]>} */
343
+ const methods = {};
344
+ manifest_data.routes.forEach((route) => {
345
+ if (route.endpoint) {
346
+ if (lookup[route.endpoint.file]) {
347
+ methods[route.endpoint.file] = lookup[route.endpoint.file].filter(is_http_method);
348
+ }
349
+ }
350
+
351
+ if (route.leaf?.server) {
352
+ if (lookup[route.leaf.server]) {
353
+ methods[route.leaf.server] = lookup[route.leaf.server].filter(is_http_method);
354
+ }
355
+ }
356
+ });
357
+
358
+ return methods;
359
+ }
@@ -0,0 +1,85 @@
1
+ import fs from 'fs';
2
+ import * as vite from 'vite';
3
+ import { s } from '../../../utils/misc.js';
4
+ import { get_config_aliases } from '../utils.js';
5
+ import { assets_base } from './utils.js';
6
+
7
+ /**
8
+ * @param {{
9
+ * config: import('types').ValidatedConfig;
10
+ * vite_config: import('vite').ResolvedConfig;
11
+ * vite_config_env: import('vite').ConfigEnv;
12
+ * manifest_data: import('types').ManifestData;
13
+ * output_dir: string;
14
+ * service_worker_entry_file: string | null;
15
+ * }} options
16
+ * @param {import('types').Prerendered} prerendered
17
+ * @param {import('vite').Manifest} client_manifest
18
+ */
19
+ export async function build_service_worker(
20
+ { config, vite_config, manifest_data, output_dir, service_worker_entry_file },
21
+ prerendered,
22
+ client_manifest
23
+ ) {
24
+ const build = new Set();
25
+ for (const key in client_manifest) {
26
+ const { file, css = [], assets = [] } = client_manifest[key];
27
+ build.add(file);
28
+ css.forEach((file) => build.add(file));
29
+ assets.forEach((file) => build.add(file));
30
+ }
31
+
32
+ const service_worker = `${config.kit.outDir}/generated/service-worker.js`;
33
+
34
+ fs.writeFileSync(
35
+ service_worker,
36
+ `
37
+ export const build = [
38
+ ${Array.from(build)
39
+ .map((file) => `${s(`${config.kit.paths.base}/${file}`)}`)
40
+ .join(',\n\t\t\t\t')}
41
+ ];
42
+
43
+ export const files = [
44
+ ${manifest_data.assets
45
+ .filter((asset) => config.kit.serviceWorker.files(asset.file))
46
+ .map((asset) => `${s(`${config.kit.paths.base}/${asset.file}`)}`)
47
+ .join(',\n\t\t\t\t')}
48
+ ];
49
+
50
+ export const prerendered = [
51
+ ${prerendered.paths.map((path) => s(path)).join(',\n\t\t\t\t')}
52
+ ];
53
+
54
+ export const version = ${s(config.kit.version.name)};
55
+ `
56
+ .replace(/^\t{3}/gm, '')
57
+ .trim()
58
+ );
59
+
60
+ await vite.build({
61
+ base: assets_base(config.kit),
62
+ build: {
63
+ lib: {
64
+ entry: /** @type {string} */ (service_worker_entry_file),
65
+ name: 'app',
66
+ formats: ['es']
67
+ },
68
+ rollupOptions: {
69
+ output: {
70
+ entryFileNames: 'service-worker.js'
71
+ }
72
+ },
73
+ outDir: `${output_dir}/client`,
74
+ emptyOutDir: false
75
+ },
76
+ define: vite_config.define,
77
+ configFile: false,
78
+ resolve: {
79
+ alias: [
80
+ ...get_config_aliases(config.kit),
81
+ { find: '$service-worker', replacement: service_worker }
82
+ ]
83
+ }
84
+ });
85
+ }
@@ -0,0 +1,230 @@
1
+ import fs from 'fs';
2
+ import path from 'path';
3
+ import * as vite from 'vite';
4
+ import { get_config_aliases, get_app_aliases } from '../utils.js';
5
+
6
+ /**
7
+ * @typedef {import('rollup').RollupOutput} RollupOutput
8
+ * @typedef {import('rollup').OutputChunk} OutputChunk
9
+ * @typedef {import('rollup').OutputAsset} OutputAsset
10
+ */
11
+
12
+ /**
13
+ * Invokes Vite.
14
+ * @param {import('vite').UserConfig} config
15
+ */
16
+ export async function create_build(config) {
17
+ const { output } = /** @type {RollupOutput} */ (
18
+ await vite.build({ ...config, configFile: false })
19
+ );
20
+
21
+ const chunks = output.filter(
22
+ /** @returns {output is OutputChunk} */ (output) => output.type === 'chunk'
23
+ );
24
+
25
+ const assets = output.filter(
26
+ /** @returns {output is OutputAsset} */ (output) => output.type === 'asset'
27
+ );
28
+
29
+ return { chunks, assets };
30
+ }
31
+
32
+ /**
33
+ * Adds transitive JS and CSS dependencies to the js and css inputs.
34
+ * @param {import('vite').Manifest} manifest
35
+ * @param {string} entry
36
+ * @param {boolean} add_dynamic_css
37
+ */
38
+ export function find_deps(manifest, entry, add_dynamic_css) {
39
+ /** @type {Set<string>} */
40
+ const seen = new Set();
41
+
42
+ /** @type {Set<string>} */
43
+ const imports = new Set();
44
+
45
+ /** @type {Set<string>} */
46
+ const stylesheets = new Set();
47
+
48
+ /** @type {Set<string>} */
49
+ const fonts = new Set();
50
+
51
+ /**
52
+ * @param {string} current
53
+ * @param {boolean} add_js
54
+ */
55
+ function traverse(current, add_js) {
56
+ if (seen.has(current)) return;
57
+ seen.add(current);
58
+
59
+ const { chunk } = resolve_symlinks(manifest, current);
60
+
61
+ if (add_js) imports.add(chunk.file);
62
+
63
+ if (chunk.assets) {
64
+ for (const asset of chunk.assets) {
65
+ if (/\.(woff2?|ttf|otf)$/.test(asset)) {
66
+ fonts.add(asset);
67
+ }
68
+ }
69
+ }
70
+
71
+ if (chunk.css) {
72
+ chunk.css.forEach((file) => stylesheets.add(file));
73
+ }
74
+
75
+ if (chunk.imports) {
76
+ chunk.imports.forEach((file) => traverse(file, add_js));
77
+ }
78
+
79
+ if (add_dynamic_css && chunk.dynamicImports) {
80
+ chunk.dynamicImports.forEach((file) => traverse(file, false));
81
+ }
82
+ }
83
+
84
+ const { chunk, file } = resolve_symlinks(manifest, entry);
85
+
86
+ traverse(file, true);
87
+
88
+ return {
89
+ file: chunk.file,
90
+ imports: Array.from(imports),
91
+ stylesheets: Array.from(stylesheets),
92
+ fonts: Array.from(fonts)
93
+ };
94
+ }
95
+
96
+ /**
97
+ * @param {import('vite').Manifest} manifest
98
+ * @param {string} file
99
+ */
100
+ export function resolve_symlinks(manifest, file) {
101
+ while (!manifest[file]) {
102
+ file = path.relative('.', fs.realpathSync(file));
103
+ }
104
+
105
+ const chunk = manifest[file];
106
+
107
+ return { chunk, file };
108
+ }
109
+
110
+ /**
111
+ * Partial Vite configuration that we use by default for setting up the build.
112
+ * Can be used in a non-SvelteKit Vite server and build process such as Storybook.
113
+ * @param {{
114
+ * config: import('types').ValidatedConfig;
115
+ * ssr: boolean;
116
+ * }} options
117
+ * @return {import('vite').UserConfig}
118
+ */
119
+ export function get_build_setup_config({ config, ssr }) {
120
+ return {
121
+ build: {
122
+ // don't use the default name to avoid collisions with 'static/manifest.json'
123
+ manifest: 'vite-manifest.json',
124
+ ssr
125
+ },
126
+ define: {
127
+ __SVELTEKIT_ADAPTER_NAME__: JSON.stringify(config.kit.adapter?.name),
128
+ __SVELTEKIT_APP_VERSION_FILE__: JSON.stringify(`${config.kit.appDir}/version.json`),
129
+ __SVELTEKIT_APP_VERSION_POLL_INTERVAL__: JSON.stringify(config.kit.version.pollInterval),
130
+ __SVELTEKIT_EMBEDDED__: config.kit.embedded ? 'true' : 'false'
131
+ },
132
+ resolve: {
133
+ alias: [...get_app_aliases(config.kit), ...get_config_aliases(config.kit)]
134
+ },
135
+ optimizeDeps: {
136
+ exclude: ['@sveltejs/kit']
137
+ },
138
+ ssr: {
139
+ noExternal: [
140
+ // TODO document why this is necessary
141
+ '@sveltejs/kit',
142
+ // This ensures that esm-env is inlined into the server output with the
143
+ // export conditions resolved correctly through Vite. This prevents adapters
144
+ // that bundle later on to resolve the export conditions incorrectly
145
+ // and for example include browser-only code in the server output
146
+ // because they for example use esbuild.build with `platform: 'browser'`
147
+ 'esm-env'
148
+ ]
149
+ }
150
+ };
151
+ }
152
+
153
+ /**
154
+ * Partial Vite configuration that we use by default for setting up the build.
155
+ * Cannot be used in a non-SvelteKit Vite server and build process such as Storybook.
156
+ * @param {{
157
+ * config: import('types').ValidatedConfig;
158
+ * input: Record<string, string>;
159
+ * ssr: boolean;
160
+ * outDir: string;
161
+ * }} options
162
+ * @return {import('vite').UserConfig}
163
+ */
164
+ export function get_build_compile_config({ config, input, ssr, outDir }) {
165
+ const prefix = `${config.kit.appDir}/immutable`;
166
+
167
+ return {
168
+ appType: 'custom',
169
+ base: ssr ? assets_base(config.kit) : './',
170
+ build: {
171
+ cssCodeSplit: true,
172
+ outDir,
173
+ rollupOptions: {
174
+ input,
175
+ output: {
176
+ format: 'esm',
177
+ entryFileNames: ssr ? '[name].js' : `${prefix}/[name]-[hash].js`,
178
+ chunkFileNames: ssr ? 'chunks/[name].js' : `${prefix}/chunks/[name]-[hash].js`,
179
+ assetFileNames: `${prefix}/assets/[name]-[hash][extname]`,
180
+ hoistTransitiveImports: false
181
+ },
182
+ preserveEntrySignatures: 'strict'
183
+ },
184
+ target: ssr ? 'node16.14' : undefined
185
+ },
186
+ publicDir: ssr ? false : config.kit.files.assets,
187
+ worker: {
188
+ rollupOptions: {
189
+ output: {
190
+ entryFileNames: `${prefix}/workers/[name]-[hash].js`,
191
+ chunkFileNames: `${prefix}/workers/chunks/[name]-[hash].js`,
192
+ hoistTransitiveImports: false
193
+ }
194
+ }
195
+ }
196
+ };
197
+ }
198
+
199
+ /**
200
+ * The Vite configuration that we use by default for building.
201
+ * @param {{
202
+ * config: import('types').ValidatedConfig;
203
+ * input: Record<string, string>;
204
+ * ssr: boolean;
205
+ * outDir: string;
206
+ * }} options
207
+ * @return {import('vite').UserConfig}
208
+ */
209
+ export function get_default_build_config(options) {
210
+ return vite.mergeConfig(get_build_setup_config(options), get_build_compile_config(options));
211
+ }
212
+
213
+ /**
214
+ * @param {import('types').ValidatedKitConfig} config
215
+ * @returns {string}
216
+ */
217
+ export function assets_base(config) {
218
+ return (config.paths.assets || config.paths.base || '.') + '/';
219
+ }
220
+
221
+ const method_names = new Set(['GET', 'HEAD', 'PUT', 'POST', 'DELETE', 'PATCH']);
222
+
223
+ // If we'd written this in TypeScript, it could be easy...
224
+ /**
225
+ * @param {string} str
226
+ * @returns {str is import('types').HttpMethod}
227
+ */
228
+ export function is_http_method(str) {
229
+ return method_names.has(str);
230
+ }