diff --git a/.changeset/rotten-gorillas-sort.md b/.changeset/rotten-gorillas-sort.md new file mode 100644 index 000000000000..95cc09630e92 --- /dev/null +++ b/.changeset/rotten-gorillas-sort.md @@ -0,0 +1,5 @@ +--- +'@sveltejs/kit': patch +--- + +[breaking] only route pages on the client-side diff --git a/documentation/docs/01-routing.md b/documentation/docs/01-routing.md index fbbd6b583a1d..aedc71670770 100644 --- a/documentation/docs/01-routing.md +++ b/documentation/docs/01-routing.md @@ -130,8 +130,6 @@ The job of this function is to return a `{ status, headers, body }` object repre - `4xx` — client error - `5xx` — server error -> For successful responses, SvelteKit will generate 304s automatically. - If the returned `body` is an object, and no `content-type` header is returned, it will automatically be turned into a JSON response. (Don't worry about `$lib`, we'll get to that [later](#modules-$lib).) > Returning nothing is equivalent to an explicit 404 response. diff --git a/documentation/docs/07-a-options.md b/documentation/docs/07-a-options.md index 9c9e0b5f7dcc..76bd55134390 100644 --- a/documentation/docs/07-a-options.md +++ b/documentation/docs/07-a-options.md @@ -34,7 +34,7 @@ In certain cases, you may wish to disable this behaviour. Adding a `sveltekit:no ### rel=external -By default, the SvelteKit runtime intercepts clicks on `` elements and bypasses the normal browser navigation for relative (same-origin) URLs that match one of your page routes. We sometimes need to tell SvelteKit that certain links need to be handled by normal browser navigation. +By default, the SvelteKit runtime intercepts clicks on `` elements and bypasses the normal browser navigation for relative (same-origin) URLs that match one of your page routes. We sometimes need to tell SvelteKit that certain links need to be handled by normal browser navigation. Examples of this might be linking to another page on your domain that's not part of your SvelteKit app or linking to an endpoint. Adding a `rel=external` attribute to a link... diff --git a/packages/kit/src/core/create_app/index.js b/packages/kit/src/core/create_app/index.js index 6293d768fc13..f31bf79152f2 100644 --- a/packages/kit/src/core/create_app/index.js +++ b/packages/kit/src/core/create_app/index.js @@ -88,8 +88,6 @@ function generate_client_manifest(manifest_data, base) { if (params) tuple.push(params); return `// ${route.a[route.a.length - 1]}\n\t\t[${tuple.join(', ')}]`; - } else { - return `// ${route.file}\n\t\t[${route.pattern}]`; } }) .join(',\n\n\t\t')} diff --git a/packages/kit/src/runtime/app/navigation.js b/packages/kit/src/runtime/app/navigation.js index bdf86d229380..0d32fca7006c 100644 --- a/packages/kit/src/runtime/app/navigation.js +++ b/packages/kit/src/runtime/app/navigation.js @@ -47,9 +47,7 @@ async function prefetchRoutes_(pathnames) { ? router.routes.filter((route) => pathnames.some((pathname) => route[0].test(pathname))) : router.routes; - const promises = matching - .filter(/** @returns {r is import('types/internal').CSRPage} */ (r) => r && r.length > 1) - .map((r) => Promise.all(r[1].map((load) => load()))); + const promises = matching.map((r) => Promise.all(r[1].map((load) => load()))); await Promise.all(promises); } diff --git a/packages/kit/src/runtime/client/renderer.js b/packages/kit/src/runtime/client/renderer.js index 79d15f9600d5..e524c1f27fc1 100644 --- a/packages/kit/src/runtime/client/renderer.js +++ b/packages/kit/src/runtime/client/renderer.js @@ -369,21 +369,13 @@ export class Renderer { for (let i = 0; i < info.routes.length; i += 1) { const route = info.routes[i]; - // check if endpoint route - if (route.length === 1) { - return { reload: true, props: {}, state: this.current }; - } - // load code for subsequent routes immediately, if they are as // likely to match the current path/query as the current one let j = i + 1; while (j < info.routes.length) { const next = info.routes[j]; if (next[0].toString() === route[0].toString()) { - // if it's a page route - if (next.length !== 1) { - next[1].forEach((loader) => loader()); - } + next[1].forEach((loader) => loader()); j += 1; } else { break; diff --git a/packages/kit/src/runtime/client/start.js b/packages/kit/src/runtime/client/start.js index 3c5a7712dfd3..5d7868f6a7e1 100644 --- a/packages/kit/src/runtime/client/start.js +++ b/packages/kit/src/runtime/client/start.js @@ -1,6 +1,6 @@ -// @ts-expect-error - value will be replaced on build step +// @ts-expect-error - doesn't exist yet. generated by Rollup import Root from 'ROOT'; -// @ts-expect-error - value will be replaced on build step +// @ts-expect-error - doesn't exist yet. generated by Rollup import { routes, fallback } from 'MANIFEST'; import { Router } from './router.js'; import { Renderer } from './renderer.js'; diff --git a/packages/kit/src/runtime/client/types.d.ts b/packages/kit/src/runtime/client/types.d.ts index 171732e36ded..225b7956dfce 100644 --- a/packages/kit/src/runtime/client/types.d.ts +++ b/packages/kit/src/runtime/client/types.d.ts @@ -1,4 +1,4 @@ -import { CSRComponent, CSRPage, CSRRoute, NormalizedLoadOutput } from 'types/internal'; +import { CSRComponent, CSRRoute, NormalizedLoadOutput } from 'types/internal'; import { Page } from 'types/page'; export type NavigationInfo = { @@ -10,7 +10,7 @@ export type NavigationInfo = { }; export type NavigationCandidate = { - route: CSRPage; + route: CSRRoute; info: NavigationInfo; }; diff --git a/packages/kit/test/apps/basics/src/routes/routing/_tests.js b/packages/kit/test/apps/basics/src/routes/routing/_tests.js index 6a3a8033b488..571aaa4ece64 100644 --- a/packages/kit/test/apps/basics/src/routes/routing/_tests.js +++ b/packages/kit/test/apps/basics/src/routes/routing/_tests.js @@ -136,14 +136,10 @@ export default function (test, is_dev) { } }); - test( - 'does not attempt client-side navigation to server routes', - '/routing', - async ({ page, clicknav }) => { - await clicknav('[href="/routing/ambiguous/ok.json"]'); - assert.equal(await page.textContent('body'), 'ok'); - } - ); + test('does not attempt client-side navigation to server routes', '/routing', async ({ page }) => { + await page.click('[href="/routing/ambiguous/ok.json"]'); + assert.equal(await page.textContent('body'), 'ok'); + }); test('allows reserved words as route names', '/routing/const', async ({ page }) => { assert.equal(await page.textContent('h1'), 'reserved words are okay as routes'); diff --git a/packages/kit/test/apps/basics/src/routes/routing/index.svelte b/packages/kit/test/apps/basics/src/routes/routing/index.svelte index 66d254aa01f8..8b97115fb5e9 100644 --- a/packages/kit/test/apps/basics/src/routes/routing/index.svelte +++ b/packages/kit/test/apps/basics/src/routes/routing/index.svelte @@ -1,7 +1,7 @@

Great success!

a -ok +ok elsewhere -
+
diff --git a/packages/kit/test/apps/basics/src/routes/routing/rest/[...rest]/_tests.js b/packages/kit/test/apps/basics/src/routes/routing/rest/[...rest]/_tests.js index 190802b9a5e8..ba2f685dc405 100644 --- a/packages/kit/test/apps/basics/src/routes/routing/rest/[...rest]/_tests.js +++ b/packages/kit/test/apps/basics/src/routes/routing/rest/[...rest]/_tests.js @@ -25,7 +25,7 @@ export default function (test) { assert.equal(await page.textContent('h1'), 'xyz/abc'); assert.equal(await page.textContent('h2'), 'xyz/abc'); - await clicknav('[href="/routing/rest/xyz/abc/qwe/deep.json"]'); + await page.click('[href="/routing/rest/xyz/abc/qwe/deep.json"]'); assert.equal(await page.textContent('body'), 'xyz/abc/qwe'); }); } diff --git a/packages/kit/test/apps/basics/src/routes/routing/rest/[...rest]/deep.svelte b/packages/kit/test/apps/basics/src/routes/routing/rest/[...rest]/deep.svelte index e0c6633cd2e4..bd442553cad3 100644 --- a/packages/kit/test/apps/basics/src/routes/routing/rest/[...rest]/deep.svelte +++ b/packages/kit/test/apps/basics/src/routes/routing/rest/[...rest]/deep.svelte @@ -16,5 +16,5 @@

{$page.params.rest}

{rest}

-deep +deep back diff --git a/packages/kit/types/internal.d.ts b/packages/kit/types/internal.d.ts index 8f9aa5105eb6..5882efcefaa5 100644 --- a/packages/kit/types/internal.d.ts +++ b/packages/kit/types/internal.d.ts @@ -103,11 +103,7 @@ export interface SSREndpoint { export type SSRRoute = SSREndpoint | SSRPage; -export type CSRPage = [RegExp, CSRComponentLoader[], CSRComponentLoader[], GetParams?]; - -export type CSREndpoint = [RegExp]; - -export type CSRRoute = CSREndpoint | CSRPage; +export type CSRRoute = [RegExp, CSRComponentLoader[], CSRComponentLoader[], GetParams?]; export interface SSRManifest { assets: Asset[];