svelte
Frameworksveltejs/svelte
A compiler that turns declarative components into efficient JavaScript.
Overview
Svelte is a frontend framework that compiles declarative components into efficient JavaScript, surgically updating the DOM. It offers a simpler, less verbose approach to building reactive user interfaces. Open-source under MIT license.
README Preview
\n \n \n \n \n\n\n[](LICENSE.md) [](https://svelte.dev/chat)\n\n## What is Svelte?\n\nSvelte is a new way to build web applications. It's a compiler that takes your declarative components and converts them into efficient JavaScript that surgically updates the DOM.\n\nLearn more at the [Svelte website](https://svelte.dev), or stop by the [Discord chatroom](https://svelte.dev/chat).\n\n## Supporting Svelte\n\nSvelte is an MIT-licensed open source project with its ongoing development made possible entirely by fantastic volunteers. If you'd like to support their efforts, please consider:\n\n- [Becoming a backer on Open Collective](https://opencollective.com/svelte).\n\nFunds donated via Open Collective will be used for compensating expenses related to Svelte's development such as hosting costs. If sufficient donations are received, funds may also be used to support Svelte's development more directly.\n\n## Roadmap\n\nYou may view [our roadmap](https://svelte.dev/roadmap) if you'd like to see what we're currently working on.\n\n## Contributing\n\nPlease see the [Contributing Guide](CONTRIBUTING.md) and the [`svelte`](packages/svelte) package for information on contributing to Svelte.\n\n## Is svelte.dev down?\n\nProbably not, but it's possible. If you can't seem to access any `.dev` sites, check out [this SuperUser question and answer](https://superuser.com/q/1413402).\n\n## License\n\n[MIT](LICENSE.md)\n
FAQ (5)
TroubleshootingHow do I fix `in` and `Object.hasOwn` not updating in a Svelte 5 `$derived` when a missing state property is added later?
This is a reactivity bug in Svelte 5.57.2. For a $derived created outside an effect—such as in a class instantiated from an event handler or a module-level store—the proxy's has trap did not track a missing key because its parent effect was null. Direct property access worked because the get trap always created a source.
It was fixed by PR #18944, which changed missing-key tracking from active_effect !== null to active_reaction !== null. Upgrade Svelte 5 to a newer release containing that fix, ideally the latest Svelte 5.x version.
As a temporary workaround, force a direct read of the property in the same derived before using in or Object.hasOwn:
has_x = $derived((this.state.x, 'x' in this.state));
owns_y = $derived((this.state.y, Object.hasOwn(this.state, 'y')));
The direct read creates the reactive property source, so adding x or y later invalidates the derived.
TroubleshootingWhy do I get "value is not defined" when using let:value with a children snippet in Svelte 5?
let: directives do not work when child content is defined with {#snippet children()}; the let:value declaration is ignored, so value is undefined. Remove let:value and receive the value through the snippet's parameter instead:
<Child>
{#snippet children({ value })}
Value is: {value}
{/snippet}
</Child>
This behavior occurs in Svelte 5, including version 5.1.0.
TroubleshootingHow to fix the Svelte 5 memory leak when a $derived is read with untrack() inside $effect or onMount?
This is caused by Svelte connecting descendant derived values during an untracked read. The derived can remain CONNECTED with reactions === null, stay registered on a long-lived source such as page.data, and retain the unmounted component context and DOM. It is reproducible in Svelte 5.57.0 with patterns such as untrack(() => get(snapshot)) inside an effect or any derived read inside onMount.
Fix it by upgrading Svelte to a 5.x release containing the derived-connection fix:
npm install svelte@latest
# or
pnpm update svelte
# or
yarn upgrade svelte --latest
Verify the installed version with npm ls svelte. After upgrading, the reproduction's final source.reactions should be undefined after the effect root is destroyed, rather than retaining a reaction.
As a temporary workaround, avoid reading complex $derived chains only inside untrack() or onMount; read raw state there or restructure the code so the derived is read by a normal tracked reactive context. The definitive fix is the Svelte patch that only connects a derived when its active reader is itself connected.
TroubleshootingHow do I fix Svelte's `state_unsafe_mutation` error when `<svelte:document bind:activeElement />` removes the focused element?
This is a known Svelte 5 bug (reported in 5.25.9). When a focused element is removed by an {#if} block, the browser fires focusout while Svelte is running the template effect, and the activeElement binding tries to update state during that effect.
Fix it by upgrading Svelte to a newer 5.x release containing the fix "don't throw state_unsafe_mutation when the focused element is removed with bind:activeElement":
npm install svelte@latest
Then restart your dev server/build.
Temporary workaround if you cannot upgrade: blur the element before removing it:
<button
onclick={(event) => {
event.currentTarget.blur();
showButton = false;
}}
>
hello
</button>
Alternatively, defer the removal with requestAnimationFrame(() => (showButton = false)).
TroubleshootingHow to fix a Svelte event handler being undefined after a top-level await in production builds?
This is a Svelte 5.57.1 compiler bug with experimental.async: true. In production, the handler is passed to $.delegated() or $.event() before code after the top-level await assigns it, so the listener is undefined. Development builds work because they read the handler lazily.
A fix is implemented in PR #18933; upgrade Svelte when it is released. Until then, use one of these workarounds:
1. Create the handler before the first await:
<script>
const make = (name) => () => console.log(name);
const onclick = make('click');
await Promise.resolve();
</script>
<button {onclick}>click</button>
2. Wrap the handler in an inline arrow function so it is read when the event fires:
<button onclick={() => onclick()}>click</button>
Verify the production result with:
vite build && vite preview