diff --git a/eslint.config.js b/eslint.config.js index 0607fe2ebca0..24853218a339 100644 --- a/eslint.config.js +++ b/eslint.config.js @@ -4,8 +4,17 @@ import svelte_config from '@sveltejs/eslint-config'; export default [ ...svelte_config, { + languageOptions: { + parserOptions: { + project: true + } + }, rules: { + '@typescript-eslint/await-thenable': 'error', +// '@typescript-eslint/no-floating-promises': 'error', +// '@typescript-eslint/no-misused-promises': 'error', '@typescript-eslint/no-unused-expressions': 'off', + '@typescript-eslint/require-await': 'error', 'no-undef': 'off' } }, @@ -15,7 +24,18 @@ export default [ 'packages/adapter-static/test/apps/*/build', 'packages/adapter-cloudflare/files', 'packages/adapter-netlify/files', - 'packages/adapter-node/files' + 'packages/adapter-node/files', + 'packages/adapter-node/rollup.config.js', + 'packages/adapter-node/tests/smoke.spec.js', + 'packages/adapter-static/test/apps', + 'packages/create-svelte/shared', + 'packages/create-svelte/templates', + 'packages/kit/src/core/sync/create_manifest_data/test/samples', + 'packages/kit/test/apps', + 'packages/kit/test/build-errors', + 'packages/kit/test/prerendering', + 'packages/package/test/errors', + 'packages/package/test/fixtures' ] } ]; diff --git a/packages/adapter-auto/index.js b/packages/adapter-auto/index.js index 983f6a1fa66c..fe720092bc79 100644 --- a/packages/adapter-auto/index.js +++ b/packages/adapter-auto/index.js @@ -36,9 +36,9 @@ function detect_package_manager() { } /** @param {string} name */ -async function import_from_cwd(name) { +function import_from_cwd(name) { const cwd = pathToFileURL(process.cwd()).href; - const url = await resolve(name, cwd + '/x.js'); + const url = resolve(name, cwd + '/x.js'); return import(url); } diff --git a/packages/adapter-netlify/index.js b/packages/adapter-netlify/index.js index 7bfec980ef9a..8f8a1c5eecd4 100644 --- a/packages/adapter-netlify/index.js +++ b/packages/adapter-netlify/index.js @@ -92,7 +92,7 @@ export default function ({ split = false, edge = edge_set_in_env_var } = {}) { await generate_edge_functions({ builder }); } else { - await generate_lambda_functions({ builder, split, publish }); + generate_lambda_functions({ builder, split, publish }); } }, @@ -182,7 +182,7 @@ async function generate_edge_functions({ builder }) { * @param { string } params.publish * @param { boolean } params.split */ -async function generate_lambda_functions({ builder, publish, split }) { +function generate_lambda_functions({ builder, publish, split }) { builder.mkdirp('.netlify/functions-internal/.svelte-kit'); /** @type {string[]} */ diff --git a/packages/adapter-node/src/handler.js b/packages/adapter-node/src/handler.js index 5586e5169622..186232c31918 100644 --- a/packages/adapter-node/src/handler.js +++ b/packages/adapter-node/src/handler.js @@ -105,7 +105,7 @@ const ssr = async (req, res) => { return; } - setResponse( + await setResponse( res, await server.respond(request, { platform: { req }, diff --git a/packages/adapter-vercel/files/serverless.js b/packages/adapter-vercel/files/serverless.js index 1a76ba8a6f29..7928d148ec7c 100644 --- a/packages/adapter-vercel/files/serverless.js +++ b/packages/adapter-vercel/files/serverless.js @@ -35,7 +35,7 @@ export default async (req, res) => { const request = await getRequest({ base: `https://${req.headers.host}`, request: req }); - setResponse( + await setResponse( res, await server.respond(request, { getClientAddress() { diff --git a/packages/create-svelte/index.js b/packages/create-svelte/index.js index b247b73a1fbb..be274e274337 100755 --- a/packages/create-svelte/index.js +++ b/packages/create-svelte/index.js @@ -3,6 +3,7 @@ import path from 'node:path'; import { mkdirp, copy, dist } from './utils.js'; /** @type {import('./types/index.js').create} */ +// eslint-disable-next-line @typescript-eslint/require-await export async function create(cwd, options) { mkdirp(cwd); diff --git a/packages/create-svelte/scripts/build-templates.js b/packages/create-svelte/scripts/build-templates.js index 4e07dfa0fc99..7d7a47240507 100644 --- a/packages/create-svelte/scripts/build-templates.js +++ b/packages/create-svelte/scripts/build-templates.js @@ -305,4 +305,4 @@ async function main() { await generate_templates(shared); } -main(); +await main(); diff --git a/packages/create-svelte/test/check.js b/packages/create-svelte/test/check.js index 91e5f3361713..b375090f8285 100644 --- a/packages/create-svelte/test/check.js +++ b/packages/create-svelte/test/check.js @@ -108,7 +108,7 @@ for (const template of templates) { const cwd = path.join(test_workspace_dir, `${template}-${types}`); fs.rmSync(cwd, { recursive: true, force: true }); - create(cwd, { + await create(cwd, { name: `create-svelte-test-${template}-${types}`, template, types, diff --git a/packages/enhanced-img/src/index.js b/packages/enhanced-img/src/index.js index bbdac4d9b5d7..97ca3e47073a 100644 --- a/packages/enhanced-img/src/index.js +++ b/packages/enhanced-img/src/index.js @@ -5,8 +5,9 @@ import { image } from './preprocessor.js'; /** * @returns {Promise} */ +// eslint-disable-next-line @typescript-eslint/require-await export async function enhancedImages() { - const imagetools_instance = await imagetools_plugin(); + const imagetools_instance = imagetools_plugin(); return !process.versions.webcontainer ? [image_plugin(imagetools_instance), imagetools_instance] : []; @@ -60,7 +61,7 @@ const fallback = { '.webp': 'png' }; -async function imagetools_plugin() { +function imagetools_plugin() { /** @type {Partial} */ const imagetools_opts = { defaultDirectives: async ({ pathname, searchParams: qs }, metadata) => { diff --git a/packages/enhanced-img/test/preprocessor.spec.js b/packages/enhanced-img/test/preprocessor.spec.js index ba48b7c79531..7e25d4f8f643 100644 --- a/packages/enhanced-img/test/preprocessor.spec.js +++ b/packages/enhanced-img/test/preprocessor.spec.js @@ -32,7 +32,7 @@ it('Image preprocess snapshot test', async () => { // Make imports readable const ouput = processed.code.replace(/import/g, '\n\timport'); - expect(ouput).toMatchFileSnapshot('./Output.svelte'); + await expect(ouput).toMatchFileSnapshot('./Output.svelte'); }); it('parses a minimized object', () => { diff --git a/packages/kit/postinstall.js b/packages/kit/postinstall.js index da908bbf8537..8d6d9ed37b8e 100644 --- a/packages/kit/postinstall.js +++ b/packages/kit/postinstall.js @@ -40,7 +40,7 @@ try { try { const config = await load_config(); - await sync.all(config, 'development'); + sync.all(config, 'development'); } catch (error) { console.error('Error while trying to sync SvelteKit config'); console.error(error); diff --git a/packages/kit/src/cli.js b/packages/kit/src/cli.js index 9cf2cfaf1afe..99c339844230 100755 --- a/packages/kit/src/cli.js +++ b/packages/kit/src/cli.js @@ -35,7 +35,7 @@ prog try { const config = await load_config(); const sync = await import('./core/sync/sync.js'); - await sync.all_types(config, mode); + sync.all_types(config, mode); } catch (error) { handle_error(error); } diff --git a/packages/kit/src/core/postbuild/prerender.js b/packages/kit/src/core/postbuild/prerender.js index f1633ab843af..20d32866836c 100644 --- a/packages/kit/src/core/postbuild/prerender.js +++ b/packages/kit/src/core/postbuild/prerender.js @@ -233,7 +233,7 @@ async function prerender({ out, manifest_path, metadata, verbose, env }) { const body = Buffer.from(await response.arrayBuffer()); - save('pages', response, body, decoded, encoded, referrer, 'linked'); + await save('pages', response, body, decoded, encoded, referrer, 'linked'); for (const [dependency_path, result] of dependencies) { // this seems circuitous, but using new URL allows us to not care @@ -257,7 +257,7 @@ async function prerender({ out, manifest_path, metadata, verbose, env }) { const body = result.body ?? new Uint8Array(await result.response.arrayBuffer()); - save( + await save( 'dependencies', result.response, body, @@ -305,7 +305,7 @@ async function prerender({ out, manifest_path, metadata, verbose, env }) { /** @type {Set} */ (expected_hashlinks.get(key)).add(decoded); } - enqueue(decoded, decode_uri(pathname), pathname); + await enqueue(decoded, decode_uri(pathname), pathname); } } } @@ -319,7 +319,7 @@ async function prerender({ out, manifest_path, metadata, verbose, env }) { * @param {string | null} referrer * @param {'linked' | 'fetched'} referenceType */ - function save(category, response, body, decoded, encoded, referrer, referenceType) { + async function save(category, response, body, decoded, encoded, referrer, referenceType) { const response_type = Math.floor(response.status / 100); const headers = Object.fromEntries(response.headers); @@ -341,7 +341,7 @@ async function prerender({ out, manifest_path, metadata, verbose, env }) { if (location) { const resolved = resolve(encoded, location); if (is_root_relative(resolved)) { - enqueue(decoded, decode_uri(resolved), resolved); + await enqueue(decoded, decode_uri(resolved), resolved); } if (!headers['x-sveltekit-normalize']) { @@ -449,6 +449,7 @@ async function prerender({ out, manifest_path, metadata, verbose, env }) { read: (file) => createReadableStream(`${config.outDir}/output/server/${file}`) }); + const entries_to_enqueue = []; for (const entry of config.prerender.entries) { if (entry === '*') { for (const [id, prerender] of prerender_map) { @@ -459,19 +460,20 @@ async function prerender({ out, manifest_path, metadata, verbose, env }) { if (processed_id.includes('[')) continue; const path = `/${get_route_segments(processed_id).join('/')}`; - enqueue(null, config.paths.base + path); + entries_to_enqueue.push({ path: config.paths.base + path }); } } } else { - enqueue(null, config.paths.base + entry); + entries_to_enqueue.push({ path: config.paths.base + entry }); } } for (const { id, entries } of route_level_entries) { for (const entry of entries) { - enqueue(null, config.paths.base + entry, undefined, id); + entries_to_enqueue.push({ path: config.paths.base + entry, id }); } } + await Promise.all(entries_to_enqueue.map(({ path, id }) => enqueue(null, path, undefined, id))); await q.done(); diff --git a/packages/kit/src/core/sync/sync.js b/packages/kit/src/core/sync/sync.js index d16466818f40..fac716f88371 100644 --- a/packages/kit/src/core/sync/sync.js +++ b/packages/kit/src/core/sync/sync.js @@ -23,7 +23,7 @@ export function init(config, mode) { * Update SvelteKit's generated files * @param {import('types').ValidatedConfig} config */ -export async function create(config) { +export function create(config) { const manifest_data = create_manifest_data({ config }); const output = path.join(config.kit.outDir, 'generated'); @@ -31,7 +31,7 @@ export async function create(config) { write_client_manifest(config.kit, manifest_data, `${output}/client`); write_server(config, output); write_root(manifest_data, output); - await write_all_types(config, manifest_data); + write_all_types(config, manifest_data); return { manifest_data }; } @@ -44,8 +44,8 @@ export async function create(config) { * @param {import('types').ManifestData} manifest_data * @param {string} file */ -export async function update(config, manifest_data, file) { - await write_types(config, manifest_data, file); +export function update(config, manifest_data, file) { + write_types(config, manifest_data, file); return { manifest_data }; } @@ -55,9 +55,9 @@ export async function update(config, manifest_data, file) { * @param {import('types').ValidatedConfig} config * @param {string} mode The Vite mode */ -export async function all(config, mode) { +export function all(config, mode) { init(config, mode); - return await create(config); + return create(config); } /** @@ -65,10 +65,10 @@ export async function all(config, mode) { * @param {import('types').ValidatedConfig} config * @param {string} mode The Vite mode */ -export async function all_types(config, mode) { +export function all_types(config, mode) { init(config, mode); const manifest_data = create_manifest_data({ config }); - await write_all_types(config, manifest_data); + write_all_types(config, manifest_data); } /** diff --git a/packages/kit/src/core/sync/write_types/index.js b/packages/kit/src/core/sync/write_types/index.js index 2c2f0fa0b5b3..778f338260c3 100644 --- a/packages/kit/src/core/sync/write_types/index.js +++ b/packages/kit/src/core/sync/write_types/index.js @@ -28,7 +28,7 @@ const cwd = process.cwd(); * @param {import('types').ValidatedConfig} config * @param {import('types').ManifestData} manifest_data */ -export async function write_all_types(config, manifest_data) { +export function write_all_types(config, manifest_data) { if (!ts) return; const types_dir = `${config.kit.outDir}/types`; @@ -133,7 +133,7 @@ export async function write_all_types(config, manifest_data) { * @param {import('types').ManifestData} manifest_data * @param {string} file */ -export async function write_types(config, manifest_data, file) { +export function write_types(config, manifest_data, file) { if (!ts) return; if (!path.basename(file).startsWith('+')) { diff --git a/packages/kit/src/core/sync/write_types/index.spec.js b/packages/kit/src/core/sync/write_types/index.spec.js index d50a4d12fa82..24fef7441e1f 100644 --- a/packages/kit/src/core/sync/write_types/index.spec.js +++ b/packages/kit/src/core/sync/write_types/index.spec.js @@ -12,7 +12,7 @@ const cwd = fileURLToPath(new URL('./test', import.meta.url)); /** * @param {string} dir */ -async function run_test(dir) { +function run_test(dir) { rimraf(path.join(cwd, dir, '.svelte-kit')); const initial = options({}, 'config'); @@ -25,22 +25,22 @@ async function run_test(dir) { const manifest = create_manifest_data({ config: /** @type {import('types').ValidatedConfig} */ (initial) }); - await write_all_types(initial, manifest); + write_all_types(initial, manifest); } -test('Creates correct $types', async () => { +test('Creates correct $types', () => { // To save us from creating a real SvelteKit project for each of the tests, // we first run the type generation directly for each test case, and then // call `tsc` to check that the generated types are valid. - await run_test('actions'); - await run_test('simple-page-shared-only'); - await run_test('simple-page-server-only'); - await run_test('simple-page-server-and-shared'); - await run_test('layout'); - await run_test('layout-advanced'); - await run_test('slugs'); - await run_test('slugs-layout-not-all-pages-have-load'); - await run_test('param-type-inference'); + run_test('actions'); + run_test('simple-page-shared-only'); + run_test('simple-page-server-only'); + run_test('simple-page-server-and-shared'); + run_test('layout'); + run_test('layout-advanced'); + run_test('slugs'); + run_test('slugs-layout-not-all-pages-have-load'); + run_test('param-type-inference'); try { execSync('pnpm testtypes', { cwd }); } catch (e) { diff --git a/packages/kit/src/exports/hooks/sequence.spec.js b/packages/kit/src/exports/hooks/sequence.spec.js index a4912bdd5790..0829e90a92e6 100644 --- a/packages/kit/src/exports/hooks/sequence.spec.js +++ b/packages/kit/src/exports/hooks/sequence.spec.js @@ -120,7 +120,7 @@ test('uses first defined preload option', async () => { const event = /** @type {import('@sveltejs/kit').RequestEvent} */ ({}); const response = await handler({ event, - resolve: async (_event, opts = {}) => { + resolve: (_event, opts = {}) => { let html = ''; const { preload = () => false } = opts; @@ -153,7 +153,7 @@ test('uses first defined filterSerializedResponseHeaders option', async () => { const event = /** @type {import('@sveltejs/kit').RequestEvent} */ ({}); const response = await handler({ event, - resolve: async (_event, opts = {}) => { + resolve: (_event, opts = {}) => { let html = ''; const { filterSerializedResponseHeaders = () => false } = opts; diff --git a/packages/kit/src/exports/node/index.js b/packages/kit/src/exports/node/index.js index 77f2a0354ad6..d59fff34efb9 100644 --- a/packages/kit/src/exports/node/index.js +++ b/packages/kit/src/exports/node/index.js @@ -103,6 +103,7 @@ function get_raw_body(req, body_size_limit) { * }} options * @returns {Promise} */ +// eslint-disable-next-line @typescript-eslint/require-await export async function getRequest({ request, base, bodySizeLimit }) { return new Request(base + request.url, { // @ts-expect-error @@ -121,6 +122,7 @@ export async function getRequest({ request, base, bodySizeLimit }) { * @param {Response} response * @returns {Promise} */ +// eslint-disable-next-line @typescript-eslint/require-await export async function setResponse(res, response) { for (const [key, value] of response.headers) { try { diff --git a/packages/kit/src/exports/vite/build/build_service_worker.js b/packages/kit/src/exports/vite/build/build_service_worker.js index cd594cdad096..a7c11188d02a 100644 --- a/packages/kit/src/exports/vite/build/build_service_worker.js +++ b/packages/kit/src/exports/vite/build/build_service_worker.js @@ -66,13 +66,13 @@ export async function build_service_worker( */ const sw_virtual_modules = { name: 'service-worker-build-virtual-modules', - async resolveId(id) { + resolveId(id) { if (id.startsWith('$env/') || id.startsWith('$app/') || id === '$service-worker') { return `\0virtual:${id}`; } }, - async load(id) { + load(id) { if (!id.startsWith('\0virtual:')) return; if (id === service_worker) { diff --git a/packages/kit/src/exports/vite/dev/index.js b/packages/kit/src/exports/vite/dev/index.js index 503cb51feb45..1c6792e431b9 100644 --- a/packages/kit/src/exports/vite/dev/index.js +++ b/packages/kit/src/exports/vite/dev/index.js @@ -97,9 +97,9 @@ export async function dev(vite, vite_config, svelte_config) { return { module, module_node, url }; } - async function update_manifest() { + function update_manifest() { try { - ({ manifest_data } = await sync.create(svelte_config)); + ({ manifest_data } = sync.create(svelte_config)); if (manifest_error) { manifest_error = null; @@ -273,7 +273,7 @@ export async function dev(vite, vite_config, svelte_config) { return error.stack; } - await update_manifest(); + update_manifest(); /** * @param {string} event @@ -377,7 +377,7 @@ export async function dev(vite, vite_config, svelte_config) { SvelteKitError: control_module_vite.SvelteKitError }); } - align_exports(); + await align_exports(); const ws_send = vite.ws.send; /** @param {any} args */ vite.ws.send = function (...args) { @@ -389,7 +389,7 @@ export async function dev(vite, vite_config, svelte_config) { return ws_send.apply(vite.ws, args); }; - vite.middlewares.use(async (req, res, next) => { + vite.middlewares.use((req, res, next) => { try { const base = `${vite.config.server.https ? 'https' : 'http'}://${ req.headers[':authority'] || req.headers.host @@ -540,7 +540,7 @@ export async function dev(vite, vite_config, svelte_config) { setResponse(res, rendered); }); } else { - setResponse(res, rendered); + await setResponse(res, rendered); } } catch (e) { const error = coalesce_to_error(e); diff --git a/packages/kit/src/exports/vite/index.js b/packages/kit/src/exports/vite/index.js index 81689ddb91da..402fa009bf64 100644 --- a/packages/kit/src/exports/vite/index.js +++ b/packages/kit/src/exports/vite/index.js @@ -131,7 +131,7 @@ const warning_preprocessor = { async function resolve_peer_dependency(dependency) { try { // @ts-expect-error the types are wrong - const resolved = await imr.resolve(dependency, pathToFileURL(process.cwd() + '/dummy.js')); + const resolved = imr.resolve(dependency, pathToFileURL(process.cwd() + '/dummy.js')); return import(resolved); } catch { throw new Error( @@ -242,7 +242,7 @@ async function kit({ svelte_config }) { * Build the SvelteKit-provided Vite config to be merged with the user's vite.config.js file. * @see https://vitejs.dev/guide/api-plugin.html#config */ - async config(config, config_env) { + config(config, config_env) { initial_config = config; vite_config_env = config_env; is_build = config_env.command === 'build'; @@ -339,7 +339,7 @@ async function kit({ svelte_config }) { }; if (!secondary_build_started) { - manifest_data = (await sync.all(svelte_config, config_env.mode)).manifest_data; + manifest_data = sync.all(svelte_config, config_env.mode).manifest_data; } } else { new_config.define = { @@ -373,7 +373,7 @@ async function kit({ svelte_config }) { const plugin_virtual_modules = { name: 'vite-plugin-sveltekit-virtual-modules', - async resolveId(id, importer) { + resolveId(id, importer) { // If importing from a service-worker, only allow $service-worker & $env/static/public, but none of the other virtual modules. // This check won't catch transitive imports, but it will warn when the import comes from a service-worker directly. // Transitive imports will be caught during the build. @@ -397,7 +397,7 @@ async function kit({ svelte_config }) { } }, - async load(id, options) { + load(id, options) { const browser = !options?.ssr; const global = is_build @@ -533,7 +533,7 @@ async function kit({ svelte_config }) { writeBundle: { sequential: true, - async handler(_options) { + handler(_options) { if (vite_config.build.ssr) return; const guard = module_guard(this, { @@ -560,7 +560,7 @@ async function kit({ svelte_config }) { * Build the SvelteKit-provided Vite config to be merged with the user's vite.config.js file. * @see https://vitejs.dev/guide/api-plugin.html#config */ - async config(config) { + config(config) { /** @type {import('vite').UserConfig} */ let new_config; diff --git a/packages/kit/src/runtime/app/forms.js b/packages/kit/src/runtime/app/forms.js index d55783116a97..da7245d1605a 100644 --- a/packages/kit/src/runtime/app/forms.js +++ b/packages/kit/src/runtime/app/forms.js @@ -104,7 +104,7 @@ export function enhance(form_element, submit = () => {}) { result.type === 'redirect' || result.type === 'error' ) { - applyAction(result); + await applyAction(result); } }; @@ -179,7 +179,7 @@ export function enhance(form_element, submit = () => {}) { result = { type: 'error', error }; } - callback({ + await callback({ action, formData: form_data, formElement: form_element, diff --git a/packages/kit/src/runtime/client/client.js b/packages/kit/src/runtime/client/client.js index df0148d4e75c..ab1ec548f9ae 100644 --- a/packages/kit/src/runtime/client/client.js +++ b/packages/kit/src/runtime/client/client.js @@ -255,13 +255,6 @@ export async function start(_app, _target, hydrate) { container = __SVELTEKIT_EMBEDDED__ ? _target : document.documentElement; target = _target; - // we import the root layout/error nodes eagerly, so that - // connectivity errors after initialisation don't nuke the app - default_layout_loader = _app.nodes[0]; - default_error_loader = _app.nodes[1]; - default_layout_loader(); - default_error_loader(); - current_history_index = history.state?.[HISTORY_INDEX]; current_navigation_index = history.state?.[NAVIGATION_INDEX]; @@ -289,11 +282,15 @@ export async function start(_app, _target, hydrate) { scrollTo(scroll.x, scroll.y); } - if (hydrate) { - await _hydrate(target, hydrate); - } else { - goto(location.href, { replaceState: true }); - } + // we import the root layout/error nodes eagerly, so that + // connectivity errors after initialisation don't nuke the app + default_layout_loader = _app.nodes[0]; + default_error_loader = _app.nodes[1]; + await Promise.allSettled([ + default_layout_loader(), + default_error_loader(), + hydrate ? _hydrate(target, hydrate) : goto(location.href, { replaceState: true }) + ]); _start_router(); } @@ -469,15 +466,7 @@ function initialize(result, target, hydrate) { * form?: Record | null; * }} opts */ -async function get_navigation_result_from_branch({ - url, - params, - branch, - status, - error, - route, - form -}) { +function get_navigation_result_from_branch({ url, params, branch, status, error, route, form }) { /** @type {import('types').TrailingSlash} */ let slash = 'never'; @@ -1017,7 +1006,7 @@ async function load_route({ id, invalidating, url, params, route, preload }) { const error_load = await load_nearest_error_page(i, branch, errors); if (error_load) { - return await get_navigation_result_from_branch({ + return get_navigation_result_from_branch({ url, params, branch: branch.slice(0, error_load.idx).concat(error_load.node), @@ -1036,7 +1025,7 @@ async function load_route({ id, invalidating, url, params, route, preload }) { } } - return await get_navigation_result_from_branch({ + return get_navigation_result_from_branch({ url, params, branch, @@ -1136,7 +1125,7 @@ async function load_root_error_page({ status, error, url, route }) { data: null }; - return await get_navigation_result_from_branch({ + return get_navigation_result_from_branch({ url, params, branch: [root_layout, root_error], @@ -1327,7 +1316,7 @@ async function navigate({ route: { id: null } }); } else { - _goto(new URL(navigation_result.location, url).href, {}, redirect_count + 1, nav_token); + await _goto(new URL(navigation_result.location, url).href, {}, redirect_count + 1, nav_token); return false; } } else if (/** @type {number} */ (navigation_result.props.page.status) >= 400) { @@ -1525,10 +1514,10 @@ function setup_preload() { container.addEventListener('touchstart', tap, { passive: true }); const observer = new IntersectionObserver( - (entries) => { + async (entries) => { for (const entry of entries) { if (entry.isIntersecting) { - _preload_code(/** @type {HTMLAnchorElement} */ (entry.target).href); + await _preload_code(/** @type {HTMLAnchorElement} */ (entry.target).href); observer.unobserve(entry.target); } } @@ -1942,7 +1931,7 @@ export async function applyAction(result) { const error_load = await load_nearest_error_page(current.branch.length, branch, route.errors); if (error_load) { - const navigation_result = await get_navigation_result_from_branch({ + const navigation_result = get_navigation_result_from_branch({ url, params: current.params, branch: branch.slice(0, error_load.idx).concat(error_load.node), @@ -1958,7 +1947,7 @@ export async function applyAction(result) { tick().then(reset_focus); } } else if (result.type === 'redirect') { - _goto(result.location, { invalidateAll: true }, 0); + await _goto(result.location, { invalidateAll: true }, 0); } else { /** @type {Record} */ root.$set({ @@ -2130,7 +2119,7 @@ function _start_router() { setTimeout(fulfil, 100); // fallback for edge case where rAF doesn't fire because e.g. tab was backgrounded }); - navigate({ + await navigate({ type: 'link', url, keepfocus: options.keepfocus, @@ -2364,7 +2353,7 @@ async function _hydrate( } } - result = await get_navigation_result_from_branch({ + result = get_navigation_result_from_branch({ url, params, branch, diff --git a/packages/kit/src/runtime/client/fetcher.js b/packages/kit/src/runtime/client/fetcher.js index 46d7a0b569a3..dd964c8144ba 100644 --- a/packages/kit/src/runtime/client/fetcher.js +++ b/packages/kit/src/runtime/client/fetcher.js @@ -18,12 +18,13 @@ export function unlock_fetch() { if (DEV && BROWSER) { let can_inspect_stack_trace = false; - // detect whether async stack traces work + // eslint-disable-next-line @typescript-eslint/require-await const check_stack_trace = async () => { const stack = /** @type {string} */ (new Error().stack); can_inspect_stack_trace = stack.includes('check_stack_trace'); }; + // detect whether async stack traces work check_stack_trace(); /** diff --git a/packages/kit/src/runtime/client/utils.js b/packages/kit/src/runtime/client/utils.js index d205f48cdc42..16a1b3426a9e 100644 --- a/packages/kit/src/runtime/client/utils.js +++ b/packages/kit/src/runtime/client/utils.js @@ -240,6 +240,7 @@ export function create_updated_store() { if (DEV || !BROWSER) { return { subscribe, + // eslint-disable-next-line @typescript-eslint/require-await check: async () => false }; } diff --git a/packages/kit/src/runtime/server/page/index.js b/packages/kit/src/runtime/server/page/index.js index b90bf67eef58..3424c5fcdce5 100644 --- a/packages/kit/src/runtime/server/page/index.js +++ b/packages/kit/src/runtime/server/page/index.js @@ -146,7 +146,7 @@ export async function render_page(event, page, options, manifest, state, resolve const data = {}; for (let j = 0; j < i; j += 1) { const parent = await server_promises[j]; - if (parent) Object.assign(data, await parent.data); + if (parent) Object.assign(data, parent.data); } return data; } diff --git a/packages/kit/src/runtime/server/page/load_data.spec.js b/packages/kit/src/runtime/server/page/load_data.spec.js index ec3167c08822..da5cc0b17203 100644 --- a/packages/kit/src/runtime/server/page/load_data.spec.js +++ b/packages/kit/src/runtime/server/page/load_data.spec.js @@ -5,6 +5,7 @@ import { create_universal_fetch } from './load_data.js'; * @param {Partial>} event */ function create_fetch(event) { + // eslint-disable-next-line @typescript-eslint/require-await event.fetch = event.fetch || (async () => new Response('foo')); event.request = event.request || new Request('doesnt:matter'); event.route = event.route || { id: 'foo' }; @@ -38,6 +39,7 @@ test('keeps body when mode isnt no-cors on same domain', async () => { test('succeeds when acao header present on cors', async () => { const fetch = create_fetch({ + // eslint-disable-next-line @typescript-eslint/require-await fetch: async () => new Response('foo', { headers: { 'access-control-allow-origin': '*' } }) }); const response = await fetch('https://domain-a.com'); @@ -48,7 +50,7 @@ test('succeeds when acao header present on cors', async () => { test('errors when no acao header present on cors', async () => { const fetch = create_fetch({}); - expect(async () => { + await expect(async () => { const response = await fetch('https://domain-b.com'); await response.text(); }).rejects.toThrowError( diff --git a/packages/kit/src/runtime/server/page/respond_with_error.js b/packages/kit/src/runtime/server/page/respond_with_error.js index 121ebc5406f2..10bf3fe0d324 100644 --- a/packages/kit/src/runtime/server/page/respond_with_error.js +++ b/packages/kit/src/runtime/server/page/respond_with_error.js @@ -50,6 +50,7 @@ export async function respond_with_error({ event, state, node: default_layout, + // eslint-disable-next-line @typescript-eslint/require-await parent: async () => ({}) }); @@ -59,6 +60,7 @@ export async function respond_with_error({ event, fetched, node: default_layout, + // eslint-disable-next-line @typescript-eslint/require-await parent: async () => ({}), resolve_opts, server_data_promise, diff --git a/packages/kit/src/utils/fork.js b/packages/kit/src/utils/fork.js index 96d513a21e6f..28dc8a798853 100644 --- a/packages/kit/src/utils/fork.js +++ b/packages/kit/src/utils/fork.js @@ -7,7 +7,7 @@ import { Worker, parentPort } from 'node:worker_threads'; * @template T * @template U * @param {string} module `import.meta.url` of the file - * @param {(opts: T) => U} callback The function that is invoked in the subprocess + * @param {(opts: T) => Promise} callback The function that is invoked in the subprocess * @returns {(opts: T) => Promise} A function that when called starts the subprocess */ export function forked(module, callback) { diff --git a/packages/kit/src/utils/streaming.spec.js b/packages/kit/src/utils/streaming.spec.js index e9fb58004abd..379dd7cc12cb 100644 --- a/packages/kit/src/utils/streaming.spec.js +++ b/packages/kit/src/utils/streaming.spec.js @@ -1,12 +1,19 @@ import { expect, test } from 'vitest'; import { create_async_iterator } from './streaming.js'; +import { fail } from 'node:assert'; test('works with fast consecutive promise resolutions', async () => { const iterator = create_async_iterator(); - Promise.resolve(1).then((n) => iterator.push(n)); - Promise.resolve(2).then((n) => iterator.push(n)); - Promise.resolve().then(() => iterator.done()); + Promise.resolve(1) + .then((n) => iterator.push(n)) + .catch(fail); + Promise.resolve(2) + .then((n) => iterator.push(n)) + .catch(fail); + Promise.resolve() + .then(() => iterator.done()) + .catch(fail); const actual = []; for await (const value of iterator.iterator) { diff --git a/packages/kit/test/utils.js b/packages/kit/test/utils.js index 38e4faaedd6c..92616c3e42ad 100644 --- a/packages/kit/test/utils.js +++ b/packages/kit/test/utils.js @@ -7,7 +7,7 @@ import { test as base, devices } from '@playwright/test'; export const test = base.extend({ app: async ({ page }, use) => { // these are assumed to have been put in the global scope by the layout - use({ + await use({ /** * @param {string} url * @param {{ replaceState?: boolean }} opts @@ -66,7 +66,7 @@ export const test = base.extend({ } } - use(clicknav); + await use(clicknav); }, in_view: async ({ page }, use) => { @@ -77,7 +77,7 @@ export const test = base.extend({ return box && view && box.y < view.height && box.y + box.height > 0; } - use(in_view); + await use(in_view); }, get_computed_style: async ({ page }, use) => { @@ -119,7 +119,7 @@ export const test = base.extend({ }, // eslint-disable-next-line no-empty-pattern - read_errors: ({}, use) => { + read_errors: async ({}, use) => { /** @param {string} path */ function read_errors(path) { const errors = @@ -128,7 +128,7 @@ export const test = base.extend({ return errors[path]; } - use(read_errors); + await use(read_errors); }, // eslint-disable-next-line no-empty-pattern diff --git a/packages/migrate/migrations/self-closing-tags/index.js b/packages/migrate/migrations/self-closing-tags/index.js index 1c11ea56c448..673a26eb38a8 100644 --- a/packages/migrate/migrations/self-closing-tags/index.js +++ b/packages/migrate/migrations/self-closing-tags/index.js @@ -50,7 +50,7 @@ export async function migrate() { /** @param {string} name */ async function import_from_cwd(name) { const cwd = pathToFileURL(process.cwd()).href; - const url = await resolve(name, cwd + '/x.js'); + const url = resolve(name, cwd + '/x.js'); return import(url); } diff --git a/packages/package/src/index.js b/packages/package/src/index.js index 6d7450182643..a6cbda297cbb 100644 --- a/packages/package/src/index.js +++ b/packages/package/src/index.js @@ -80,7 +80,7 @@ export async function watch(options) { const watcher = chokidar.watch(input, { ignoreInitial: true }); const ready = new Promise((resolve) => watcher.on('ready', resolve)); - watcher.on('all', async (type, filepath) => { + watcher.on('all', (type, filepath) => { const file = analyze(path.relative(input, filepath), extensions); pending.push({ file, type }); diff --git a/packages/package/test/index.js b/packages/package/test/index.js index 73667f593266..d4bec434d114 100644 --- a/packages/package/test/index.js +++ b/packages/package/test/index.js @@ -227,7 +227,7 @@ if (!process.env.CI) { await settled(); compare('post-error.svelte'); } finally { - watcher.close(); + await watcher.close(); remove('src/lib/Test.svelte'); remove('src/lib/a.js');