Skip to content

fix(kit): normalise Node.js Buffer to Uint8Array in SSR hydration to prevent pool bytes leaking into the page - #16814

Open
okxint wants to merge 452 commits into
sveltejs:mainfrom
okxint:fix/buffer-ssr-hydration-pool-leak
Open

fix(kit): normalise Node.js Buffer to Uint8Array in SSR hydration to prevent pool bytes leaking into the page#16814
okxint wants to merge 452 commits into
sveltejs:mainfrom
okxint:fix/buffer-ssr-hydration-pool-leak

Conversation

@okxint

@okxint okxint commented Aug 15, 2026

Copy link
Copy Markdown

closes #16603

What

Node.js Buffer is a Uint8Array view into a shared 8 KiB pool ArrayBuffer. When a remote query returns a Buffer, devalue.uneval() serialises the entire backing pool and uses .subarray(offset, end) to address the bytes. The pool contains arbitrary uninitialised data; any bytes outside the ASCII range produce U+FFFD replacement characters in the HTML, which makes the inline <script> block syntactically invalid:

Uncaught SyntaxError: illegal character U+FFFD

The page is broken on direct load / refresh. A plain Uint8Array with the same values works fine because it has its own backing ArrayBuffer.

Fix

Intercept Buffer instances in create_replacer and emit new Uint8Array([...]) from the buffer's own bytes. new Uint8Array(buffer) copies by value (not by reference into the pool), so devalue only serialises the bytes that matter.

+  if (globalThis.Buffer?.isBuffer(thing)) {
+    return `new Uint8Array([${new Uint8Array(thing)}])`;
+  }

Tests

Added packages/kit/src/runtime/server/utils.spec.js with 5 unit tests:

  • serialises a regular Buffer to new Uint8Array([...])
  • serialises an empty Buffer
  • verifies a Buffer.allocUnsafe (pool-backed) emits only its own bytes, not the pool
  • confirms the transport-encoded path is unaffected
  • confirms plain Uint8Array still goes through the default devalue path

All tests pass with vitest run --config kit.vitest.config.js.


Please don't delete this checklist! Before submitting the PR, please make sure you do the following:

  • It's really useful if your PR references an issue where it is discussed ahead of time. In many cases, features are absent for a reason. For large changes, please create an RFC: https://github.com/sveltejs/rfcs
  • This message body should clearly illustrates what problems it solves.
  • Include a test that fails without this PR but passes with it.

Tests

  • Run the tests with pnpm test and lint the project with pnpm lint and pnpm check

Changesets

  • Changeset added (.changeset/fix-buffer-ssr-pool-leak.md, patch)

Rich-Harris and others added 30 commits June 4, 2026 13:49
This PR was opened by the [Changesets
release](https://github.com/changesets/action) GitHub action. When
you're ready to do a release, you can merge this and the packages will
be published to npm automatically. If you're not ready to do a release
yet, that's fine, whenever you add more changesets to version-3, this PR
will be updated.

⚠️⚠️⚠️⚠️⚠️⚠️

`version-3` is currently in **pre mode** so this branch has prereleases
rather than normal releases. If you want to exit prereleases, run
`changeset pre exit` on `version-3`.

⚠️⚠️⚠️⚠️⚠️⚠️

# Releases
## @sveltejs/adapter-auto@8.0.0-next.0

### Major Changes


- breaking: require SvelteKit 3
([sveltejs#15506](sveltejs#15506))


### Patch Changes

- Updated dependencies
[[`fa335bd`](sveltejs@fa335bd),
[`3031d89`](sveltejs@3031d89),
[`cb9d416`](sveltejs@cb9d416),
[`caf3a18`](sveltejs@caf3a18),
[`4777827`](sveltejs@4777827),
[`a2792e2`](sveltejs@a2792e2),
[`ba36148`](sveltejs@ba36148),
[`48e8710`](sveltejs@48e8710),
[`e2f3075`](sveltejs@e2f3075),
[`047d6a0`](sveltejs@047d6a0),
[`87603d1`](sveltejs@87603d1),
[`096962c`](sveltejs@096962c),
[`d545970`](sveltejs@d545970),
[`e2f3075`](sveltejs@e2f3075),
[`d06affc`](sveltejs@d06affc),
[`8af47eb`](sveltejs@8af47eb),
[`e2f3075`](sveltejs@e2f3075),
[`5c4d130`](sveltejs@5c4d130),
[`3f11f35`](sveltejs@3f11f35),
[`caf3a18`](sveltejs@caf3a18),
[`8823037`](sveltejs@8823037),
[`1d76212`](sveltejs@1d76212),
[`0dc0548`](sveltejs@0dc0548),
[`00d81fa`](sveltejs@00d81fa)]:
  - @sveltejs/kit@3.0.0-next.0
## @sveltejs/adapter-cloudflare@8.0.0-next.0

### Major Changes


- breaking: upgrade `@cloudflare/workers-types` to 4.20260219.0
([sveltejs#15347](sveltejs#15347))


- breaking: upgrade minimum `wrangler` version to ^4.67.0
([sveltejs#15347](sveltejs#15347))


- breaking: remove `platform.context` in favour of `platform.ctx`
([sveltejs#15347](sveltejs#15347))


- breaking: require SvelteKit 3
([sveltejs#15506](sveltejs#15506))


### Patch Changes


- chore: check the `WORKERS_CI` environment variable to determine if
we're building for Cloudflare Workers
([sveltejs#13733](sveltejs#13733))

- Updated dependencies
[[`fa335bd`](sveltejs@fa335bd),
[`3031d89`](sveltejs@3031d89),
[`cb9d416`](sveltejs@cb9d416),
[`caf3a18`](sveltejs@caf3a18),
[`4777827`](sveltejs@4777827),
[`a2792e2`](sveltejs@a2792e2),
[`ba36148`](sveltejs@ba36148),
[`48e8710`](sveltejs@48e8710),
[`e2f3075`](sveltejs@e2f3075),
[`047d6a0`](sveltejs@047d6a0),
[`87603d1`](sveltejs@87603d1),
[`096962c`](sveltejs@096962c),
[`d545970`](sveltejs@d545970),
[`e2f3075`](sveltejs@e2f3075),
[`d06affc`](sveltejs@d06affc),
[`8af47eb`](sveltejs@8af47eb),
[`e2f3075`](sveltejs@e2f3075),
[`5c4d130`](sveltejs@5c4d130),
[`3f11f35`](sveltejs@3f11f35),
[`caf3a18`](sveltejs@caf3a18),
[`8823037`](sveltejs@8823037),
[`1d76212`](sveltejs@1d76212),
[`0dc0548`](sveltejs@0dc0548),
[`00d81fa`](sveltejs@00d81fa)]:
  - @sveltejs/kit@3.0.0-next.0
## @sveltejs/adapter-netlify@7.0.0-next.0

### Major Changes


- chore: use `rolldown` for edge function bundling
([sveltejs#15432](sveltejs#15432))


- breaking: write output that conforms to the stable [Netlify Frameworks
API](https://docs.netlify.com/build/frameworks/frameworks-api/).
([sveltejs#15294](sveltejs#15294))
  
Deploying and previewing with Netlify CLI now requires
[v17.31.0](https://github.com/netlify/cli/releases/tag/v17.31.0) or
later. Run `npm i -g netlify-cli@latest` to upgrade.

- breaking: require SvelteKit 3
([sveltejs#15506](sveltejs#15506))


- breaking: edge function build target is now `es2022`
([sveltejs#15432](sveltejs#15432))


### Patch Changes

- Updated dependencies
[[`fa335bd`](sveltejs@fa335bd),
[`3031d89`](sveltejs@3031d89),
[`cb9d416`](sveltejs@cb9d416),
[`caf3a18`](sveltejs@caf3a18),
[`4777827`](sveltejs@4777827),
[`a2792e2`](sveltejs@a2792e2),
[`ba36148`](sveltejs@ba36148),
[`48e8710`](sveltejs@48e8710),
[`e2f3075`](sveltejs@e2f3075),
[`047d6a0`](sveltejs@047d6a0),
[`87603d1`](sveltejs@87603d1),
[`096962c`](sveltejs@096962c),
[`d545970`](sveltejs@d545970),
[`e2f3075`](sveltejs@e2f3075),
[`d06affc`](sveltejs@d06affc),
[`8af47eb`](sveltejs@8af47eb),
[`e2f3075`](sveltejs@e2f3075),
[`5c4d130`](sveltejs@5c4d130),
[`3f11f35`](sveltejs@3f11f35),
[`caf3a18`](sveltejs@caf3a18),
[`8823037`](sveltejs@8823037),
[`1d76212`](sveltejs@1d76212),
[`0dc0548`](sveltejs@0dc0548),
[`00d81fa`](sveltejs@00d81fa)]:
  - @sveltejs/kit@3.0.0-next.0
## @sveltejs/adapter-node@6.0.0-next.0

### Major Changes


- chore: migrate from rollup to rolldown
([sveltejs#15297](sveltejs#15297))


- breaking: require SvelteKit 3
([sveltejs#15506](sveltejs#15506))


### Patch Changes

- Updated dependencies
[[`fa335bd`](sveltejs@fa335bd),
[`3031d89`](sveltejs@3031d89),
[`cb9d416`](sveltejs@cb9d416),
[`caf3a18`](sveltejs@caf3a18),
[`4777827`](sveltejs@4777827),
[`a2792e2`](sveltejs@a2792e2),
[`ba36148`](sveltejs@ba36148),
[`48e8710`](sveltejs@48e8710),
[`e2f3075`](sveltejs@e2f3075),
[`047d6a0`](sveltejs@047d6a0),
[`87603d1`](sveltejs@87603d1),
[`096962c`](sveltejs@096962c),
[`d545970`](sveltejs@d545970),
[`e2f3075`](sveltejs@e2f3075),
[`d06affc`](sveltejs@d06affc),
[`8af47eb`](sveltejs@8af47eb),
[`e2f3075`](sveltejs@e2f3075),
[`5c4d130`](sveltejs@5c4d130),
[`3f11f35`](sveltejs@3f11f35),
[`caf3a18`](sveltejs@caf3a18),
[`8823037`](sveltejs@8823037),
[`1d76212`](sveltejs@1d76212),
[`0dc0548`](sveltejs@0dc0548),
[`00d81fa`](sveltejs@00d81fa)]:
  - @sveltejs/kit@3.0.0-next.0
## @sveltejs/adapter-static@4.0.0-next.0

### Major Changes


- breaking: require SvelteKit 3
([sveltejs#15506](sveltejs#15506))


### Patch Changes

- Updated dependencies
[[`fa335bd`](sveltejs@fa335bd),
[`3031d89`](sveltejs@3031d89),
[`cb9d416`](sveltejs@cb9d416),
[`caf3a18`](sveltejs@caf3a18),
[`4777827`](sveltejs@4777827),
[`a2792e2`](sveltejs@a2792e2),
[`ba36148`](sveltejs@ba36148),
[`48e8710`](sveltejs@48e8710),
[`e2f3075`](sveltejs@e2f3075),
[`047d6a0`](sveltejs@047d6a0),
[`87603d1`](sveltejs@87603d1),
[`096962c`](sveltejs@096962c),
[`d545970`](sveltejs@d545970),
[`e2f3075`](sveltejs@e2f3075),
[`d06affc`](sveltejs@d06affc),
[`8af47eb`](sveltejs@8af47eb),
[`e2f3075`](sveltejs@e2f3075),
[`5c4d130`](sveltejs@5c4d130),
[`3f11f35`](sveltejs@3f11f35),
[`caf3a18`](sveltejs@caf3a18),
[`8823037`](sveltejs@8823037),
[`1d76212`](sveltejs@1d76212),
[`0dc0548`](sveltejs@0dc0548),
[`00d81fa`](sveltejs@00d81fa)]:
  - @sveltejs/kit@3.0.0-next.0
## @sveltejs/adapter-vercel@7.0.0-next.0

### Major Changes


- chore: use `rolldown` for edge function bundling
([sveltejs#15432](sveltejs#15432))


- breaking: edge function build target is now `es2022`
([sveltejs#15432](sveltejs#15432))


### Patch Changes

- Updated dependencies
[[`fa335bd`](sveltejs@fa335bd),
[`3031d89`](sveltejs@3031d89),
[`cb9d416`](sveltejs@cb9d416),
[`caf3a18`](sveltejs@caf3a18),
[`4777827`](sveltejs@4777827),
[`a2792e2`](sveltejs@a2792e2),
[`ba36148`](sveltejs@ba36148),
[`48e8710`](sveltejs@48e8710),
[`e2f3075`](sveltejs@e2f3075),
[`047d6a0`](sveltejs@047d6a0),
[`87603d1`](sveltejs@87603d1),
[`096962c`](sveltejs@096962c),
[`d545970`](sveltejs@d545970),
[`e2f3075`](sveltejs@e2f3075),
[`d06affc`](sveltejs@d06affc),
[`8af47eb`](sveltejs@8af47eb),
[`e2f3075`](sveltejs@e2f3075),
[`5c4d130`](sveltejs@5c4d130),
[`3f11f35`](sveltejs@3f11f35),
[`caf3a18`](sveltejs@caf3a18),
[`8823037`](sveltejs@8823037),
[`1d76212`](sveltejs@1d76212),
[`0dc0548`](sveltejs@0dc0548),
[`00d81fa`](sveltejs@00d81fa)]:
  - @sveltejs/kit@3.0.0-next.0
## @sveltejs/enhanced-img@1.0.0-next.0

### Major Changes


- breaking: require Node 22 or newer
([sveltejs#12548](sveltejs#12548))


### Minor Changes


- breaking: require Vite 8 and `vite-plugin-svelte` 7
([sveltejs#15542](sveltejs#15542))
## @sveltejs/kit@3.0.0-next.0

### Major Changes


- breaking: TypeScript 6 is now the minimum required version
([sveltejs#15930](sveltejs#15930))


- breaking: upgrade to cookie v1. Cookie names must now contain only
ASCII characters ([sveltejs#13386](sveltejs#13386))


- breaking: require Node 22 or newer
([sveltejs#12548](sveltejs#12548))


- breaking: remove the `preloadStrategy` option. `modulepreload` will
always be used ([sveltejs#15256](sveltejs#15256))


- breaking: default the cookie `path` option to `'/'`
([sveltejs#15398](sveltejs#15398))


- breaking: remove `@sveltejs/kit/node/polyfills`
([sveltejs#15430](sveltejs#15430))


- breaking: add `config.kit.output.linkHeaderPreload` to preload using
the `Link` header ([sveltejs#15939](sveltejs#15939))


- breaking: require `@sveltejs/vite-plugin-svelte` v7
([sveltejs#15371](sveltejs#15371))


- breaking: remove `createEntries` from the `Builder` object passed to
adapter functions ([sveltejs#15509](sveltejs#15509))


- breaking: remove the deprecated CSRF `checkOrigin` option in favor of
`trustedOrigins` ([sveltejs#15437](sveltejs#15437))


- breaking: the `delta` property now only exists for `popstate`
navigation events ([sveltejs#15522](sveltejs#15522))


- breaking: remove deprecated `pragma` header in version polling for
improved CORS support
([sveltejs#15428](sveltejs#15428))


- breaking: require Svelte 5.48.0 or newer
([sveltejs#15371](sveltejs#15371))


- chore: change `error`, `isHttpError`, `redirect`, and `isRedirect` to
refer to public type instead of internal class
([sveltejs#15250](sveltejs#15250))


- breaking: require Vite 8. Provides new functionality even for existing
Vite 8 users such as faster builds with Vite hook filters and more
powerful SvelteKit adapters with the Vite environment API
([sveltejs#15371](sveltejs#15371))


- breaking: remove `data-sveltekit-*` option `'off'` in favour of
`false` ([sveltejs#15907](sveltejs#15907))


### Minor Changes


- feat: resolve paths using the Vite config `root` option instead of
`process.cwd()` to better support monorepo configurations such as Vitest
workspaces ([sveltejs#15469](sveltejs#15469))


- chore: deprecate `Response` helpers in favor of platform-provided
alternatives ([sveltejs#15448](sveltejs#15448))


- feat: explicit env vars
([sveltejs#15934](sveltejs#15934))


### Patch Changes


- fix: remove check for svelte.config.js before running `sync`
([sveltejs#15946](sveltejs#15946))


- fix: generate a placeholder tsconfig.json to squelch sync-time
warnings ([sveltejs#15948](sveltejs#15948))


- chore: remove dependency on kleur
([sveltejs#12548](sveltejs#12548))


- chore: remove dependency on `set-cookie-parser`
([sveltejs#15384](sveltejs#15384))


- fix: allow use of `$app/env/public` in service workers
([sveltejs#15950](sveltejs#15950))
## @sveltejs/package@3.0.0-next.0

### Major Changes


- breaking: require Node 22 or newer
([sveltejs#12548](sveltejs#12548))


### Patch Changes


- chore: remove dependency on kleur
([sveltejs#12548](sveltejs#12548))

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
… dependencies import it (sveltejs#15964)

Stumbled on this while updating svelte.dev to use v3 — some dependencies
(like Vercel Speed Insights) import `$app/environment`, so we need to
keep it as an importable module (albeit one that will get red squigglies
if you have it in your own code).

It's _possible_ that the same will be true of `$env/*`, but I doubt it

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [ ] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [ ] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [x] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.
This PR was opened by the [Changesets
release](https://github.com/changesets/action) GitHub action. When
you're ready to do a release, you can merge this and the packages will
be published to npm automatically. If you're not ready to do a release
yet, that's fine, whenever you add more changesets to version-3, this PR
will be updated.

⚠️⚠️⚠️⚠️⚠️⚠️

`version-3` is currently in **pre mode** so this branch has prereleases
rather than normal releases. If you want to exit prereleases, run
`changeset pre exit` on `version-3`.

⚠️⚠️⚠️⚠️⚠️⚠️

# Releases
## @sveltejs/kit@3.0.0-next.1

### Patch Changes


- fix: reinstate `$app/environment` as an alias for `$app/env`, in case
dependencies import it
([sveltejs#15964](sveltejs#15964))

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
We need to update the explicit environment variables docs to solve the
preview error deployment. It's looking for `$app/environment` types but
they've been removed when we merged `main` in
https://github.com/sveltejs/svelte.dev/actions/runs/27088756592/job/79948243995#step:10:25

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [ ] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [ ] This message body should clearly illustrate what problems it
solves.
- [ ] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [ ] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [ ] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [ ] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.

---------

Co-authored-by: vercel[bot] <35613825+vercel[bot]@users.noreply.github.com>
Co-authored-by: Rich Harris <rich.harris@vercel.com>
This PR was opened by the [Changesets
release](https://github.com/changesets/action) GitHub action. When
you're ready to do a release, you can merge this and the packages will
be published to npm automatically. If you're not ready to do a release
yet, that's fine, whenever you add more changesets to version-3, this PR
will be updated.

⚠️⚠️⚠️⚠️⚠️⚠️

`version-3` is currently in **pre mode** so this branch has prereleases
rather than normal releases. If you want to exit prereleases, run
`changeset pre exit` on `version-3`.

⚠️⚠️⚠️⚠️⚠️⚠️

# Releases
## @sveltejs/kit@3.0.0-next.2

### Patch Changes


- fix: use SSE for `query.live`
([sveltejs#15957](sveltejs#15957))


- fix: use forward slashes in the generated `env.d.ts` import path on
Windows ([sveltejs#15977](sveltejs#15977))


- fix: avoid importing Vite while validating explicit environment
variables ([sveltejs#15953](sveltejs#15953))


- docs: adjust the release version of explicit env vars
([sveltejs#15968](sveltejs#15968))


- fix: ensure `version` is defined when importing from `$app/env` with
explicit environment variables
([sveltejs#15971](sveltejs#15971))

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
This PR was opened by the [Changesets
release](https://github.com/changesets/action) GitHub action. When
you're ready to do a release, you can merge this and the packages will
be published to npm automatically. If you're not ready to do a release
yet, that's fine, whenever you add more changesets to version-3, this PR
will be updated.

⚠️⚠️⚠️⚠️⚠️⚠️

`version-3` is currently in **pre mode** so this branch has prereleases
rather than normal releases. If you want to exit prereleases, run
`changeset pre exit` on `version-3`.

⚠️⚠️⚠️⚠️⚠️⚠️

# Releases
## @sveltejs/kit@3.0.0-next.3

### Minor Changes


- feat: allow queries to refresh other queries
([sveltejs#16012](sveltejs#16012))


### Patch Changes


- fix: dedupe remote data
([sveltejs#15991](sveltejs#15991))


- fix: skip client build if all routes have CSR disabled
([sveltejs#15936](sveltejs#15936))

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
This PR was opened by the [Changesets
release](https://github.com/changesets/action) GitHub action. When
you're ready to do a release, you can merge this and the packages will
be published to npm automatically. If you're not ready to do a release
yet, that's fine, whenever you add more changesets to version-3, this PR
will be updated.

⚠️⚠️⚠️⚠️⚠️⚠️

`version-3` is currently in **pre mode** so this branch has prereleases
rather than normal releases. If you want to exit prereleases, run
`changeset pre exit` on `version-3`.

⚠️⚠️⚠️⚠️⚠️⚠️

# Releases
## @sveltejs/kit@3.0.0-next.4

### Patch Changes


- fix: reset queries before navigating when `invalidateAll` is set
([sveltejs#16014](sveltejs#16014))

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
…s#15998)

fixes
https://bsky.app/profile/peterreeves.bsky.social/post/3mnmomeazos2t

This PR fixes a regression when consolidating the workspace root path.
The Vite function is important to find where the hoisted/symlinked
packages are stored.

After merging this, we can probably remove
https://github.com/sveltejs/svelte.dev/blob/0f7fe1eb930af4e2234c792bb09a290367e6c090/apps/svelte.dev/vite.config.ts#L97
too

EDIT: tests are failing on version-3 branch because of prerendered
treeshaking having a bug

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [ ] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [ ] This message body should clearly illustrate what problems it
solves.
- [ ] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [ ] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [ ] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [ ] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.
teemingc and others added 25 commits July 21, 2026 21:48
The module ID has no references. Must be a leftover after the changes
from adding $app/manifest?
…ss inside queries (sveltejs#16452)

Closes sveltejs#16416 with the error option which seems like the right approach
to me. No hard feelings if it goes.

- `event.url`, `event.params` and `event.route` now throw on access
inside `query`, `query.batch` and `query.live`, during SSR as well,
matching how prerendering already treats `url.search`. The router runs
on the client-sent `x-sveltekit-pathname` header to produce
`event.params` and `event.route.id`, so hiding only `url` would leave
the same footgun readable through `params`.
- The error message points at the migration, pass the value as a query
argument. Reading trusted context from `locals` via `handle` still
works, but since query requests no longer carry the page URL, `handle`
sees the URL of the remote endpoint, so that context has to come from
cookies or headers.
- `command` and `form` are unchanged when called directly. Remote
functions called while a query is running inherit the restriction, since
their results feed the same cached response.
- `handleValidationError` receives an event it can read `url` on, and
prerendered data lookups inside queries resolve against the request URL
rather than `event.url`.
- Query clients stop sending the `x-sveltekit-pathname` and
`x-sveltekit-search` headers, and the server only applies them when they
are present, which also fixes the query half of sveltejs#15749.
- The test from sveltejs#14606 asserting queries can read the url is inverted,
and the remote-functions docs bullet now documents the error.

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [x] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [x] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [x] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.

---------

Co-authored-by: Rich Harris <hello@rich-harris.dev>
…error page (sveltejs#16381)

After an error page renders, `current.route` is `null`
(`load_root_error_page` stores `route: null` in the navigation state).
The next navigation computes

```js
const route_changed = current.route ? route.id !== current.route.id : false;
```

so the route counts as unchanged no matter where the user goes next. A
root layout server load that tracked `route` is then skipped as fresh,
and its data from before the error page renders on the new page. The new
test's failing assertion on `version-3` shows the layout still claiming
the previous route:

```
Expected: "/b"
Received: "/a"
```

A missing `current.route` now counts as changed. On a first-ever
navigation the flag is irrelevant, the node has no previous data to
reuse anyway, so the only behavior change is the conservative refetch
after error pages.

The interaction was never designed. `route: null` came in sveltejs#6552 to give
`beforeNavigate` a value meaning "no matched route", and the guard came
two months later in sveltejs#7450 with route tracking itself, mirroring the
adjacent `url_changed` null-guard. Neither discussed the error-page
case.

The test lives in the no-ssr app. Its root layout gains a server load
returning `route.id`, the navigation's data request is intercepted with
a 500 to produce the error page, and the follow-up navigation must show
the new route id. The app's root `+layout.server.js` was an empty file,
shipped by sveltejs#11354 so its 404-loop test has a server load node in dev;
giving it a real load keeps that trigger intact.

Found while reviewing sveltejs#16380, which mirrors this computation for the
error page itself and carries the same one-line fix.

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [x] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [x] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [x] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.
closes sveltejs#16468

Warns but keeps working, same as the v2 `files` deprecation. The docs
recommend `resolve.tsconfigPaths` per the issue; its friction with the
generated tsconfig is tracked in sveltejs#16471.

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [x] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [x] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [x] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.

---------

Co-authored-by: Tee Ming <chewteeming01@gmail.com>
Co-authored-by: vercel[bot] <35613825+vercel[bot]@users.noreply.github.com>
These were missing for the Netlify and static adapters
Standardises the Netlify adapter docs so that they're similar in
structure to the other adapter docs
…s#16461)

Supersedes sveltejs#16428. It had the right approach, but we were actually
handling `refresh` wrong in the first place. I thought we'd implemented
this behavior but somehow we haven't.

Anyway, this kills two birds with one stone:
- It makes sure we allow `.refresh` (and `.set`) to run during render
- It makes `.refresh` lazy: Calling `.refresh` busts the cache and
guarantees that the cache will be populated by the end of the request.
If you `await` the query or access its data, it will immediately run and
populate the cache; otherwise SvelteKit will do it at the end of the
request, in parallel with any other refreshing queries
closes sveltejs#14315

This PR adds a utility for checking the spelling of hook files, checks
the spelling for the universal hook file, and checks if an s is missing
from "hooks". Also, only bothers with the check if the file itself has
not been created.

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [x] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [x] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [ ] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.
The `.wrangler` directory is generated by Cloudflare Wrangler when
running the Wrangler worker preview and is placed relative to the
wrangler config. This should be ignored no matter where it is, not just
the root of the workspace
Prevents queries from infinitely looping during the drain phase. This
has the side effect of preventing multiple refreshes of the same query
during the drain phase, so... don't do that
…lds.foo.as(...) (sveltejs#16331)

closes sveltejs#16321

Made the form ID a suffix so it's easier to read in the browser's
inspector.

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [x] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [x] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [x] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.

---------

Co-authored-by: Rich Harris <rich.harris@vercel.com>
The Vercel server handler files are in a `files` directory. This
directory is where bundled output goes into for all the other adapter
packages except for the Vercel adapter. As a result, it was accidentally
included in the eslint ignore list.

This PR changes that so it's no longer ignored (alternatively, we should
just rename it as `src/`?)
Pairs with sveltejs#16450.

The way we handle TypeScript configuration is a little bit messy,
particularly as it regards service workers, which need to be in their
own TypeScript project. This PR tidies things up a bit. It will need
corresponding work to happen to the default project template.
Essentially, a SvelteKit 3 project only needs this `tsconfig.json` file:

```json
{
  "extends": "$app/tsconfig"
}
```

A service worker should live in a `src/service-worker/index.ts` file
(_not_ a `src/service-worker.ts` file, though this will still work) with
a sibling `tsconfig.json` like this:

```json
{
  "extends": "$app/tsconfig/service-worker"
}
```

You can add whatever other configuration you like there, though it's
important that the first one `"excludes"` the service worker, and that
both contain `"types": ["$app/types"]` if those options are overridden.

In addition to those two modules — which are 'real' modules in the sense
that they live in `node_modules/$app` — we introduce a third,
`$app/service-worker`, which exists solely to make it easier to get a
correctly-typed `self` object (without this, there is a lot of [annoying
boilerplate](https://svelte.dev/docs/kit/service-workers#Inside-the-service-worker)):

```ts
import { self } from '$app/service-worker';
```

> In future, we could also use this module for e.g. offline caching
strategies and the like.

I've tested the `node_modules/$app` approach with pnpm and it seems like
a winner. `$` is an invalid character for an npm package but valid for
Node's module resolution algorithm, so it works without danger of
clobbering. pnpm doesn't nuke the directory when it installs or
uninstalls packages (much like things like `node_modules/.vite`). We
could extend this idea to other modules, which would help with [this
very longstanding issue](sveltejs#1485).

TODO:

- [x] docs
- [x] validation of `types` and `exclude`
- [x] tidy up

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [x] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [x] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [x] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.

---------

Co-authored-by: vercel[bot] <35613825+vercel[bot]@users.noreply.github.com>
Co-authored-by: Vercel <vercel[bot]@users.noreply.github.com>
…veltejs#16490)

closes sveltejs#11932

Makes sense to split this off from
sveltejs#16464 since it's a relatively
simple change. Technically, this means we're 100% on the environment
API, but everything still runs on Node.js only. Main benefit is that we
have separate module graphs between the client and server now and one
step closer to adopting other parts of the environment API (fetchable
dev environments)

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [x] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [ ] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [ ] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [ ] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.

---------

Co-authored-by: vercel[bot] <35613825+vercel[bot]@users.noreply.github.com>
Co-authored-by: Vercel <vercel[bot]@users.noreply.github.com>
Co-authored-by: Nic Polumeyv <nicolas.polum@outlook.com>
Co-authored-by: Rich Harris <rich.harris@vercel.com>
closes sveltejs#16469

Does a number of things to check the version more often:
- Adds a header to responses with the version, so that any request
SvelteKit initiates is an opportunity to discover the client needs an
update
- Checks the version on `visibilitychange` and `window.focus` events
- Polls once an hour

---------

Co-authored-by: Rich Harris <richard.a.harris@gmail.com>
This deletes the weirdo `$service-worker` module now that it's no longer
necessary (because of `$app/manifest` and the availability of `$app/env`
and `$app/paths` in the service worker) and overhauls our docs to use
the new `$app/tsconfig/service-worker` etc

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [x] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [x] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [x] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.

---------

Co-authored-by: vercel[bot] <35613825+vercel[bot]@users.noreply.github.com>
Co-authored-by: Vercel <vercel[bot]@users.noreply.github.com>
This PR was opened by the [Changesets
release](https://github.com/changesets/action) GitHub action. When
you're ready to do a release, you can merge this and the packages will
be published to npm automatically. If you're not ready to do a release
yet, that's fine, whenever you add more changesets to version-3, this PR
will be updated.

⚠️⚠️⚠️⚠️⚠️⚠️

`version-3` is currently in **pre mode** so this branch has prereleases
rather than normal releases. If you want to exit prereleases, run
`changeset pre exit` on `version-3`.

⚠️⚠️⚠️⚠️⚠️⚠️

# Releases
## @sveltejs/kit@3.0.0-next.12

### Major Changes

- breaking: rename `Pathname` type to `Path` and `Asset` to `AssetPath`
([sveltejs#16430](sveltejs#16430))
  breaking: remove leading `/` from `Path` and `AssetPath`
- breaking: write tsconfig to `node_modules/$app/tsconfig`
([sveltejs#16458](sveltejs#16458))

- breaking: error on `event.url`, `event.params` and `event.route`
access inside queries
([sveltejs#16452](sveltejs#16452))

- breaking: delete `$service-worker` module
([sveltejs#16450](sveltejs#16450))

- breaking: detect new deployments on data, remote, and form action
responses, tab focus, and visibility change, and default
`version.pollInterval` to 1 hour
([sveltejs#16496](sveltejs#16496))

### Minor Changes

- feat: add `$app/manifest` module with `immutable`, `assets`,
`prerendered`, and `routes` exports
([sveltejs#16372](sveltejs#16372))

- feat: validate that all remote form fields were created with
form.fields.foo.as(...)
([sveltejs#16331](sveltejs#16331))

- feat: make `$app/paths` importable in service workers
([sveltejs#16441](sveltejs#16441))

- feat: `$app/service-worker` module
([sveltejs#16458](sveltejs#16458))

- feat: better tsconfig validation
([sveltejs#16458](sveltejs#16458))

- fix: default cookies to `secure` to `false` during development
([sveltejs#16462](sveltejs#16462))

### Patch Changes

- fix: allow `undefined` values to be passed to form field `.as(...)`
where applicable ([sveltejs#15681](sveltejs#15681))

- fix: include queries refreshed from within another query in the
serialized response
([sveltejs#16461](sveltejs#16461))

- fix: generate sourcemaps for remote modules
([sveltejs#16440](sveltejs#16440))

- fix: avoid empty getElementById() call on hash routing navigation
([sveltejs#16448](sveltejs#16448))

- fix: warn if hook files are spelled as "hook" instead of "hooks"
([sveltejs#16483](sveltejs#16483))

- chore: deprecate the `alias` option
([sveltejs#16470](sveltejs#16470))

- fix: prevent infinite loops when server-side queries refresh each
other in a cycle during the single-flight drain
([sveltejs#16461](sveltejs#16461))

- fix: populate `version` in service workers
([sveltejs#16434](sveltejs#16434))

- fix: resolve remote modules as external during dev prebundling so
packages can re-export remote functions
([sveltejs#16426](sveltejs#16426))

- fix: refetch route-tracking server data when navigating away from an
error page ([sveltejs#16381](sveltejs#16381))

- fix: serialize `query(...).set(...)`/`query(...).refresh()` values
into the rendered HTML when called from within a query during SSR
([sveltejs#16461](sveltejs#16461))

- fix: fall back to the page's form actions when a sibling endpoint has
no POST handler ([sveltejs#16349](sveltejs#16349))

- fix: return a lightweight 404 instead of rendering the error page for
subresource requests
([sveltejs#16463](sveltejs#16463))

- fix: preserve stripped path prefixes by making trailing-slash
redirects relative
([sveltejs#16431](sveltejs#16431))

- chore: deduplicate type-stripping logic in `tweak_types`
([sveltejs#16454](sveltejs#16454))

- fix: more informative error message when running a command inside a
query or prerender function
([`eb5c973`](sveltejs@eb5c973))
## @sveltejs/adapter-cloudflare@8.0.0-next.3

### Patch Changes

- chore: bump `@cloudflare/workers-types` to `4.20260621.1`
([sveltejs#16455](sveltejs#16455))
- Updated dependencies
[[`adc4c5b`](sveltejs@adc4c5b),
[`ecb0701`](sveltejs@ecb0701),
[`4b4cc60`](sveltejs@4b4cc60),
[`7390dbe`](sveltejs@7390dbe),
[`2e71340`](sveltejs@2e71340),
[`c87bc3a`](sveltejs@c87bc3a),
[`af15c6c`](sveltejs@af15c6c),
[`c6fa431`](sveltejs@c6fa431),
[`bfe4dea`](sveltejs@bfe4dea),
[`df7dc72`](sveltejs@df7dc72),
[`5ae11a1`](sveltejs@5ae11a1),
[`781205c`](sveltejs@781205c),
[`c87bc3a`](sveltejs@c87bc3a),
[`a1bfeb9`](sveltejs@a1bfeb9),
[`c87bc3a`](sveltejs@c87bc3a),
[`9f0127d`](sveltejs@9f0127d),
[`4b4cc60`](sveltejs@4b4cc60),
[`8f5b9c7`](sveltejs@8f5b9c7),
[`c9b5544`](sveltejs@c9b5544),
[`fe1d4a4`](sveltejs@fe1d4a4),
[`4b4cc60`](sveltejs@4b4cc60),
[`5f78e95`](sveltejs@5f78e95),
[`25510fc`](sveltejs@25510fc),
[`c99a6cf`](sveltejs@c99a6cf),
[`17a45ca`](sveltejs@17a45ca),
[`2ca20c3`](sveltejs@2ca20c3),
[`eb5c973`](sveltejs@eb5c973)]:
  - @sveltejs/kit@3.0.0-next.12
## @sveltejs/adapter-netlify@7.0.0-next.4

### Patch Changes

- fix: await `init` on every request to prevent race condition
([sveltejs#16467](sveltejs#16467))

- chore: bump Rolldown to `1.2.0`
([sveltejs#16455](sveltejs#16455))
- Updated dependencies
[[`adc4c5b`](sveltejs@adc4c5b),
[`ecb0701`](sveltejs@ecb0701),
[`4b4cc60`](sveltejs@4b4cc60),
[`7390dbe`](sveltejs@7390dbe),
[`2e71340`](sveltejs@2e71340),
[`c87bc3a`](sveltejs@c87bc3a),
[`af15c6c`](sveltejs@af15c6c),
[`c6fa431`](sveltejs@c6fa431),
[`bfe4dea`](sveltejs@bfe4dea),
[`df7dc72`](sveltejs@df7dc72),
[`5ae11a1`](sveltejs@5ae11a1),
[`781205c`](sveltejs@781205c),
[`c87bc3a`](sveltejs@c87bc3a),
[`a1bfeb9`](sveltejs@a1bfeb9),
[`c87bc3a`](sveltejs@c87bc3a),
[`9f0127d`](sveltejs@9f0127d),
[`4b4cc60`](sveltejs@4b4cc60),
[`8f5b9c7`](sveltejs@8f5b9c7),
[`c9b5544`](sveltejs@c9b5544),
[`fe1d4a4`](sveltejs@fe1d4a4),
[`4b4cc60`](sveltejs@4b4cc60),
[`5f78e95`](sveltejs@5f78e95),
[`25510fc`](sveltejs@25510fc),
[`c99a6cf`](sveltejs@c99a6cf),
[`17a45ca`](sveltejs@17a45ca),
[`2ca20c3`](sveltejs@2ca20c3),
[`eb5c973`](sveltejs@eb5c973)]:
  - @sveltejs/kit@3.0.0-next.12
## @sveltejs/adapter-node@6.0.0-next.6

### Patch Changes

- fix: preserve stripped path prefixes by making trailing-slash
redirects relative
([sveltejs#16431](sveltejs#16431))

- chore: bump Rolldown to `1.2.0`
([sveltejs#16455](sveltejs#16455))
- Updated dependencies
[[`adc4c5b`](sveltejs@adc4c5b),
[`ecb0701`](sveltejs@ecb0701),
[`4b4cc60`](sveltejs@4b4cc60),
[`7390dbe`](sveltejs@7390dbe),
[`2e71340`](sveltejs@2e71340),
[`c87bc3a`](sveltejs@c87bc3a),
[`af15c6c`](sveltejs@af15c6c),
[`c6fa431`](sveltejs@c6fa431),
[`bfe4dea`](sveltejs@bfe4dea),
[`df7dc72`](sveltejs@df7dc72),
[`5ae11a1`](sveltejs@5ae11a1),
[`781205c`](sveltejs@781205c),
[`c87bc3a`](sveltejs@c87bc3a),
[`a1bfeb9`](sveltejs@a1bfeb9),
[`c87bc3a`](sveltejs@c87bc3a),
[`9f0127d`](sveltejs@9f0127d),
[`4b4cc60`](sveltejs@4b4cc60),
[`8f5b9c7`](sveltejs@8f5b9c7),
[`c9b5544`](sveltejs@c9b5544),
[`fe1d4a4`](sveltejs@fe1d4a4),
[`4b4cc60`](sveltejs@4b4cc60),
[`5f78e95`](sveltejs@5f78e95),
[`25510fc`](sveltejs@25510fc),
[`c99a6cf`](sveltejs@c99a6cf),
[`17a45ca`](sveltejs@17a45ca),
[`2ca20c3`](sveltejs@2ca20c3),
[`eb5c973`](sveltejs@eb5c973)]:
  - @sveltejs/kit@3.0.0-next.12
## @sveltejs/adapter-vercel@7.0.0-next.3

### Patch Changes

- fix: await `init` on every request to prevent race condition
([sveltejs#16467](sveltejs#16467))

- chore: bump Rolldown to `1.2.0`
([sveltejs#16455](sveltejs#16455))
- Updated dependencies
[[`adc4c5b`](sveltejs@adc4c5b),
[`ecb0701`](sveltejs@ecb0701),
[`4b4cc60`](sveltejs@4b4cc60),
[`7390dbe`](sveltejs@7390dbe),
[`2e71340`](sveltejs@2e71340),
[`c87bc3a`](sveltejs@c87bc3a),
[`af15c6c`](sveltejs@af15c6c),
[`c6fa431`](sveltejs@c6fa431),
[`bfe4dea`](sveltejs@bfe4dea),
[`df7dc72`](sveltejs@df7dc72),
[`5ae11a1`](sveltejs@5ae11a1),
[`781205c`](sveltejs@781205c),
[`c87bc3a`](sveltejs@c87bc3a),
[`a1bfeb9`](sveltejs@a1bfeb9),
[`c87bc3a`](sveltejs@c87bc3a),
[`9f0127d`](sveltejs@9f0127d),
[`4b4cc60`](sveltejs@4b4cc60),
[`8f5b9c7`](sveltejs@8f5b9c7),
[`c9b5544`](sveltejs@c9b5544),
[`fe1d4a4`](sveltejs@fe1d4a4),
[`4b4cc60`](sveltejs@4b4cc60),
[`5f78e95`](sveltejs@5f78e95),
[`25510fc`](sveltejs@25510fc),
[`c99a6cf`](sveltejs@c99a6cf),
[`17a45ca`](sveltejs@17a45ca),
[`2ca20c3`](sveltejs@2ca20c3),
[`eb5c973`](sveltejs@eb5c973)]:
  - @sveltejs/kit@3.0.0-next.12

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
…veltejs#16494)

Prerendering validates each expected fragment link with
`hashlinks.includes(id)` against the target page's array of element ids,
which is O(A*L) for A ids and L inbound fragment links. Storing the
crawled ids as a `Set` makes it O(A + L).

Cost for a page with N anchors and N inbound fragment links (Node 22):

| N | array `includes` | `Set` (incl. construction) |
| ---: | ---: | ---: |
| 1,000 | 21 ms | 0.5 ms |
| 4,000 | 123 ms | 0.8 ms |
| 8,000 | 616 ms | 1.7 ms |
| 16,000 | 1,591 ms | 3.8 ms |

This mainly benefits large heavily cross-linked prerendered sites such
as generated API references.

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:

- [ ] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [x] Ideally, include a test that fails without this PR but passes with
it.

### Tests

- [x] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets

- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. All changesets should be `patch` until
SvelteKit 2.0 (major releases only that fix regressions)

### Edits

- [ ] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.
…#16510)

`data-sveltekit-preload-data` fails intermittently under server-side
route resolution, about 1 in 6 locally on `version-3`, and anything that
shifts hydration timing makes it worse (a one-line import change on
sveltejs#16308 took it to 3 failed retries in CI).

The test navigates between phases with the cursor still parked over the
previous phase's link. When the fresh page hydrates, Chromium fires a
mouse event at that position and the router preloads that link's target,
so the phase that expects zero requests counts a preload it never
triggered. A request timeline shows the target's `__route.js`, node
script and `__data.json` all arriving before the phase's `goto`
resolves, ahead of any hover.

Parking the mouse before each navigation removes the carryover. 10 of 10
runs green under `ROUTER_RESOLUTION=server` with the change.

---

### Please don't delete this checklist! Before submitting the PR, please
make sure you do the following:
- [x] It's really useful if your PR references an issue where it is
discussed ahead of time. In many cases, features are absent for a
reason. For large changes, please create an RFC:
https://github.com/sveltejs/rfcs
- [x] This message body should clearly illustrate what problems it
solves.
- [x] Ideally, include a test that fails without this PR but passes with
it.

### Tests
- [x] Run the tests with `pnpm test` and lint the project with `pnpm
lint` and `pnpm check`

### Changesets
- [x] If your PR makes a change that should be noted in one or more
packages' changelogs, generate a changeset by running `pnpm changeset`
and following the prompts. Changesets that add features should be
`minor` and those that fix bugs should be `patch`. Please prefix
changeset messages with `feat:`, `fix:`, or `chore:`.

### Edits

- [x] Please ensure that 'Allow edits from maintainers' is checked. PRs
without this option may be closed.
…o prevent pool leak in SSR hydration

Node.js Buffer is a Uint8Array view into a shared 8 KiB pool. When
devalue.uneval() serialises a Buffer returned from a remote query, it
embeds the *entire* backing pool ArrayBuffer into the page and addresses
the slice with .subarray(offset, end). The pool contains arbitrary
uninitialised bytes; any that fall outside the ASCII range produce
U+FFFD replacement characters in the HTML, causing

  Uncaught SyntaxError: illegal character U+FFFD

on the client and breaking the whole page on hard refresh.

Fix: intercept Buffer values in create_replacer and emit
`new Uint8Array([...])` from the buffer's own bytes instead, which
devalue already handles correctly for plain Uint8Array inputs.

Fixes sveltejs#16603

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@pkg-svelte-dev

Copy link
Copy Markdown

Install the latest version of @sveltejs/kit from 10640b8:

pnpm add https://pkg.svelte.dev/@sveltejs/kit/c/10640b80730cf82a9fc9bb427022d500cd8b600f

Open in pkg.svelte.dev: https://pkg.svelte.dev/repos/kit/pr/16814

Note

This PR is from a fork. A maintainer must approve approve each commit before it can be built and installed.

@changeset-bot

changeset-bot Bot commented Aug 15, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 10640b8

The changes in this PR will be included in the next version bump.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel vercel Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Additional Suggestions:

  1. Built-in Buffer normalization short-circuits before the user transport encoder loop, silently bypassing a user-registered custom Buffer encoder
  1. The SSR load-data serializer's replacer does not normalize Node.js Buffer values, so a load function returning a pooled Buffer leaks the entire 8 KiB pool ArrayBuffer into the SSR HTML and triggers illegal character U+FFFD hydration errors.

Fix on Vercel

@teemingc

Copy link
Copy Markdown
Member

Hi there. We might be solving this at the devalue layer instead sveltejs/devalue#175 can you take a look at that to see if it would solve the issue?

@okxint

okxint commented Aug 17, 2026

Copy link
Copy Markdown
Author

Thanks for the pointer! I looked at sveltejs/devalue#175 — the two fixes address different bugs.

What devalue#175 fixes: Buffer.toString() decodes bytes as UTF-8 instead of printing integers. Buffer.alloc(4, 65) becomes new Uint8Array([AAAA]) instead of new Uint8Array([65,65,65,65]). The fix builds the element list from the TypedArray constructor name ("Uint8Array") rather than the instance constructor (Buffer), so Array.from() iterates numeric values correctly.

What this PR fixes: Buffer.allocUnsafe (and Buffer.from/Buffer.concat on small inputs) allocates from Node's 8 KiB shared pool. The backing ArrayBuffer is the whole pool, not just the bytes you wrote. Even after devalue#175, uneval(Buffer.allocUnsafe(4)) would still emit new Uint8Array([/* 8192 values from the pool */]) — the wrong element count, not wrong element representation.

Evidence: Both problems are visible with a quick script:

import * as devalue from 'devalue';
// Even with the devalue PR applied, allocUnsafe still leaks:
const buf = Buffer.allocUnsafe(4);
buf.writeUInt32BE(0xdeadbeef, 0);
const s = devalue.uneval(buf);
console.log(s.length);     // >> 4 (with this kit PR's replacer)
                             // >> 8192 (without it, even after devalue#175)

The two fixes are complementary: devalue#175 corrects the element representation; this PR prevents the pool from being embedded in the first place. Both are needed for pooled Buffers to be safe. Happy to adjust the approach if you'd prefer the guard to live somewhere else in kit, or to close this and add a follow-up note to devalue#175 about the pool-size issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.