diff --git a/.changeset/wild-coins-live.md b/.changeset/wild-coins-live.md new file mode 100644 index 000000000000..b6b989ba8425 --- /dev/null +++ b/.changeset/wild-coins-live.md @@ -0,0 +1,5 @@ +--- +'@sveltejs/kit': patch +--- + +fix: correctly navigate when hash router is enabled and the browser encodes extra hashes diff --git a/packages/kit/src/runtime/client/client.js b/packages/kit/src/runtime/client/client.js index c91bb818355b..56c3855aa436 100644 --- a/packages/kit/src/runtime/client/client.js +++ b/packages/kit/src/runtime/client/client.js @@ -306,7 +306,7 @@ export async function start(_app, _target, hydrate) { if (hydrate) { await _hydrate(target, hydrate); } else { - goto(location.href, { replaceState: true }); + goto(app.hash ? decodeURIComponent(location.href) : location.href, { replaceState: true }); } _start_router(); @@ -2395,7 +2395,7 @@ function _start_router() { // (surprisingly!) mutates `current.url`, allowing us to // detect it and trigger a navigation if (current.url.hash === location.hash) { - navigate({ type: 'goto', url: current.url }); + navigate({ type: 'goto', url: new URL(decodeURIComponent(current.url.href)) }); } } }); diff --git a/packages/kit/test/apps/hash-based-routing/test/test.js b/packages/kit/test/apps/hash-based-routing/test/test.js index ae379c55f601..6743639fec2c 100644 --- a/packages/kit/test/apps/hash-based-routing/test/test.js +++ b/packages/kit/test/apps/hash-based-routing/test/test.js @@ -55,6 +55,14 @@ test.describe('hash based navigation', () => { await expect(page.locator('p')).toHaveText('a'); }); + test('navigation works with URL encoded characters', async ({ page }) => { + await page.goto('/#/%23test'); + await expect(page.locator('p')).toHaveText('home'); + // hashchange event + await page.goto('/#/a%23test'); + await expect(page.locator('p')).toHaveText('a'); + }); + test('route id and params are correct', async ({ page }) => { await page.goto('/#/b/123'); await expect(page.locator('p[data-data]')).toHaveText('{"slug":"123"} /b/[slug] /#/b/123');