From bb00d5b6e75da491bcee7860d3428458fd2f46ef Mon Sep 17 00:00:00 2001
From: "github-actions[bot]"
<41898282+github-actions[bot]@users.noreply.github.com>
Date: Fri, 6 Feb 2026 15:05:08 -0500
Subject: [PATCH 1/3] Version Packages (#17615)
Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
---
.changeset/chatty-mammals-find.md | 5 -----
.changeset/clear-olives-share.md | 5 -----
.changeset/fix-each-bind-store-logical.md | 5 -----
.changeset/fix-menu-element-a11y-roles.md | 5 -----
.changeset/forty-worlds-attack.md | 5 -----
.changeset/loud-bottles-own.md | 5 -----
.changeset/orange-ants-greet.md | 5 -----
.changeset/poor-students-nail.md | 5 -----
.changeset/sharp-snakes-poke.md | 5 -----
.changeset/tiny-owls-pay.md | 5 -----
packages/svelte/CHANGELOG.md | 26 +++++++++++++++++++++++
packages/svelte/package.json | 2 +-
packages/svelte/src/version.js | 2 +-
13 files changed, 28 insertions(+), 52 deletions(-)
delete mode 100644 .changeset/chatty-mammals-find.md
delete mode 100644 .changeset/clear-olives-share.md
delete mode 100644 .changeset/fix-each-bind-store-logical.md
delete mode 100644 .changeset/fix-menu-element-a11y-roles.md
delete mode 100644 .changeset/forty-worlds-attack.md
delete mode 100644 .changeset/loud-bottles-own.md
delete mode 100644 .changeset/orange-ants-greet.md
delete mode 100644 .changeset/poor-students-nail.md
delete mode 100644 .changeset/sharp-snakes-poke.md
delete mode 100644 .changeset/tiny-owls-pay.md
diff --git a/.changeset/chatty-mammals-find.md b/.changeset/chatty-mammals-find.md
deleted file mode 100644
index 373dc0059a..0000000000
--- a/.changeset/chatty-mammals-find.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-'svelte': patch
----
-
-fix: ensure infinite effect loops are cleared after flushing
diff --git a/.changeset/clear-olives-share.md b/.changeset/clear-olives-share.md
deleted file mode 100644
index 975b2b21b6..0000000000
--- a/.changeset/clear-olives-share.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-'svelte': patch
----
-
-fix: allow `{#key NaN}`
diff --git a/.changeset/fix-each-bind-store-logical.md b/.changeset/fix-each-bind-store-logical.md
deleted file mode 100644
index 1327015124..0000000000
--- a/.changeset/fix-each-bind-store-logical.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-'svelte': patch
----
-
-fix: detect store in each block expression regardless of AST shape
diff --git a/.changeset/fix-menu-element-a11y-roles.md b/.changeset/fix-menu-element-a11y-roles.md
deleted file mode 100644
index 75cfe8d310..0000000000
--- a/.changeset/fix-menu-element-a11y-roles.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-'svelte': patch
----
-
-fix: treat `
`/`` for a11y role checks
diff --git a/.changeset/forty-worlds-attack.md b/.changeset/forty-worlds-attack.md
deleted file mode 100644
index 52bb3644c0..0000000000
--- a/.changeset/forty-worlds-attack.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-'svelte': patch
----
-
-fix: add vite-ignore comment inside dynamic crypto import
diff --git a/.changeset/loud-bottles-own.md b/.changeset/loud-bottles-own.md
deleted file mode 100644
index 493dc6c47f..0000000000
--- a/.changeset/loud-bottles-own.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-'svelte': patch
----
-
-chore: wrap JSDoc URLs in `@see` and `@link` tags
diff --git a/.changeset/orange-ants-greet.md b/.changeset/orange-ants-greet.md
deleted file mode 100644
index 6f7c684fee..0000000000
--- a/.changeset/orange-ants-greet.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-'svelte': minor
----
-
-feat: allow use of createContext when instantiating components programmatically
diff --git a/.changeset/poor-students-nail.md b/.changeset/poor-students-nail.md
deleted file mode 100644
index cee650c002..0000000000
--- a/.changeset/poor-students-nail.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-"svelte": patch
----
-
-fix: properly hydrate already-resolved async blocks
diff --git a/.changeset/sharp-snakes-poke.md b/.changeset/sharp-snakes-poke.md
deleted file mode 100644
index 7f7f8aa7b2..0000000000
--- a/.changeset/sharp-snakes-poke.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-'svelte': patch
----
-
-fix: emit `each_key_duplicate` error in production
diff --git a/.changeset/tiny-owls-pay.md b/.changeset/tiny-owls-pay.md
deleted file mode 100644
index ac25500258..0000000000
--- a/.changeset/tiny-owls-pay.md
+++ /dev/null
@@ -1,5 +0,0 @@
----
-'svelte': patch
----
-
-fix: exit resolved async blocks on correct node when hydrating
diff --git a/packages/svelte/CHANGELOG.md b/packages/svelte/CHANGELOG.md
index a71effd5dd..b251e778ef 100644
--- a/packages/svelte/CHANGELOG.md
+++ b/packages/svelte/CHANGELOG.md
@@ -1,5 +1,31 @@
# svelte
+## 5.50.0
+
+### Minor Changes
+
+- feat: allow use of createContext when instantiating components programmatically ([#17575](https://github.com/sveltejs/svelte/pull/17575))
+
+### Patch Changes
+
+- fix: ensure infinite effect loops are cleared after flushing ([#17601](https://github.com/sveltejs/svelte/pull/17601))
+
+- fix: allow `{#key NaN}` ([#17642](https://github.com/sveltejs/svelte/pull/17642))
+
+- fix: detect store in each block expression regardless of AST shape ([#17636](https://github.com/sveltejs/svelte/pull/17636))
+
+- fix: treat ``/`` for a11y role checks ([#17638](https://github.com/sveltejs/svelte/pull/17638))
+
+- fix: add vite-ignore comment inside dynamic crypto import ([#17623](https://github.com/sveltejs/svelte/pull/17623))
+
+- chore: wrap JSDoc URLs in `@see` and `@link` tags ([#17617](https://github.com/sveltejs/svelte/pull/17617))
+
+- fix: properly hydrate already-resolved async blocks ([#17641](https://github.com/sveltejs/svelte/pull/17641))
+
+- fix: emit `each_key_duplicate` error in production ([#16724](https://github.com/sveltejs/svelte/pull/16724))
+
+- fix: exit resolved async blocks on correct node when hydrating ([#17640](https://github.com/sveltejs/svelte/pull/17640))
+
## 5.49.2
### Patch Changes
diff --git a/packages/svelte/package.json b/packages/svelte/package.json
index 48f492783f..82d0d1a8ed 100644
--- a/packages/svelte/package.json
+++ b/packages/svelte/package.json
@@ -2,7 +2,7 @@
"name": "svelte",
"description": "Cybernetically enhanced web apps",
"license": "MIT",
- "version": "5.49.2",
+ "version": "5.50.0",
"type": "module",
"types": "./types/index.d.ts",
"engines": {
diff --git a/packages/svelte/src/version.js b/packages/svelte/src/version.js
index 31538c3fe7..3aefb2e1f6 100644
--- a/packages/svelte/src/version.js
+++ b/packages/svelte/src/version.js
@@ -4,5 +4,5 @@
* The current version, as set in package.json.
* @type {string}
*/
-export const VERSION = '5.49.2';
+export const VERSION = '5.50.0';
export const PUBLIC_VERSION = '5';
From 9749ee869c4a3473a50a3a42daa2ee8896d41898 Mon Sep 17 00:00:00 2001
From: 7nik
Date: Sat, 7 Feb 2026 01:09:42 +0200
Subject: [PATCH 2/3] chore: add xhtml tests (#17597)
* add xhtml tests
* unused
* tweak
* more tests
* tweak
* we don't need to actually check the HTML - if it's malformed in SSR or mount, it will throw
* same here
* unused, so we can revert this
* and this
---------
Co-authored-by: Rich Harris
---
eslint.config.js | 1 +
packages/svelte/tests/html_equal.js | 16 ++++++++--------
.../samples/attribute-quotes/_config.js | 3 +++
.../samples/attribute-quotes/main.svelte | 2 ++
.../samples/autoclosed-tags/_config.js | 3 +++
.../samples/autoclosed-tags/main.svelte | 6 ++++++
.../samples/boolean-attributes/_config.js | 5 +++++
.../samples/boolean-attributes/main.svelte | 1 +
.../samples/comment-marker/_config.js | 3 +++
.../samples/comment-marker/main.svelte | 1 +
.../runtime-xhtml/samples/is-xhtml/_config.js | 8 ++++++++
.../samples/is-xhtml/main.svelte | 5 +++++
.../samples/void-tags/_config.js | 3 +++
.../samples/void-tags/main.svelte | 15 +++++++++++++++
packages/svelte/tests/runtime-xhtml/test.ts | 9 +++++++++
vitest-xhtml-environment.ts | 19 +++++++++++++++++++
16 files changed, 92 insertions(+), 8 deletions(-)
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/attribute-quotes/_config.js
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/attribute-quotes/main.svelte
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/autoclosed-tags/_config.js
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/autoclosed-tags/main.svelte
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/boolean-attributes/_config.js
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/boolean-attributes/main.svelte
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/comment-marker/_config.js
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/comment-marker/main.svelte
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/is-xhtml/_config.js
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/is-xhtml/main.svelte
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/void-tags/_config.js
create mode 100644 packages/svelte/tests/runtime-xhtml/samples/void-tags/main.svelte
create mode 100644 packages/svelte/tests/runtime-xhtml/test.ts
create mode 100644 vitest-xhtml-environment.ts
diff --git a/eslint.config.js b/eslint.config.js
index 0e0e0bc729..04d9294394 100644
--- a/eslint.config.js
+++ b/eslint.config.js
@@ -102,6 +102,7 @@ export default [
'playgrounds/sandbox/**',
// exclude top level config files
'*.config.js',
+ 'vitest-xhtml-environment.ts',
// documentation can contain invalid examples
'documentation',
'tmp/**'
diff --git a/packages/svelte/tests/html_equal.js b/packages/svelte/tests/html_equal.js
index 76a4a957a5..cdb8f52e37 100644
--- a/packages/svelte/tests/html_equal.js
+++ b/packages/svelte/tests/html_equal.js
@@ -9,7 +9,9 @@ function clean_children(node, opts) {
let previous = null;
let has_element_children = false;
let template =
- node.nodeName === 'TEMPLATE' ? /** @type {HTMLTemplateElement} */ (node) : undefined;
+ node.nodeName.toUpperCase() === 'TEMPLATE'
+ ? /** @type {HTMLTemplateElement} */ (node)
+ : undefined;
if (template) {
const div = document.createElement('div');
@@ -23,22 +25,20 @@ function clean_children(node, opts) {
});
attributes.forEach((attr) => {
- node.removeAttribute(attr.name);
+ if (attr.name !== 'xmlns') node.removeAttribute(attr.name);
});
- attributes.forEach((attr) => {
+ attributes.forEach(({ name, value }) => {
// Strip out the special onload/onerror hydration events from the test output
- if ((attr.name === 'onload' || attr.name === 'onerror') && attr.value === 'this.__e=event') {
+ if (['onload', 'onerror', 'xmlns'].includes(name) && value === 'this.__e=event') {
return;
}
- let value = attr.value;
-
- if (attr.name === 'class') {
+ if (name === 'class') {
value = value.replace(/svelte-\w+/, 'svelte-xyz123');
}
- node.setAttribute(attr.name, value);
+ node.setAttribute(name, value);
});
for (let child of [...node.childNodes]) {
diff --git a/packages/svelte/tests/runtime-xhtml/samples/attribute-quotes/_config.js b/packages/svelte/tests/runtime-xhtml/samples/attribute-quotes/_config.js
new file mode 100644
index 0000000000..f47bee71df
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/attribute-quotes/_config.js
@@ -0,0 +1,3 @@
+import { test } from '../../test';
+
+export default test({});
diff --git a/packages/svelte/tests/runtime-xhtml/samples/attribute-quotes/main.svelte b/packages/svelte/tests/runtime-xhtml/samples/attribute-quotes/main.svelte
new file mode 100644
index 0000000000..82db611c12
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/attribute-quotes/main.svelte
@@ -0,0 +1,2 @@
+
+
diff --git a/packages/svelte/tests/runtime-xhtml/samples/autoclosed-tags/_config.js b/packages/svelte/tests/runtime-xhtml/samples/autoclosed-tags/_config.js
new file mode 100644
index 0000000000..f47bee71df
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/autoclosed-tags/_config.js
@@ -0,0 +1,3 @@
+import { test } from '../../test';
+
+export default test({});
diff --git a/packages/svelte/tests/runtime-xhtml/samples/autoclosed-tags/main.svelte b/packages/svelte/tests/runtime-xhtml/samples/autoclosed-tags/main.svelte
new file mode 100644
index 0000000000..18a4463ce1
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/autoclosed-tags/main.svelte
@@ -0,0 +1,6 @@
+
+
+
+
+
+
diff --git a/packages/svelte/tests/runtime-xhtml/samples/boolean-attributes/_config.js b/packages/svelte/tests/runtime-xhtml/samples/boolean-attributes/_config.js
new file mode 100644
index 0000000000..f965e04b02
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/boolean-attributes/_config.js
@@ -0,0 +1,5 @@
+import { test } from '../../test';
+
+export default test({
+ skip: true
+});
diff --git a/packages/svelte/tests/runtime-xhtml/samples/boolean-attributes/main.svelte b/packages/svelte/tests/runtime-xhtml/samples/boolean-attributes/main.svelte
new file mode 100644
index 0000000000..3d2fc88d10
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/boolean-attributes/main.svelte
@@ -0,0 +1 @@
+
diff --git a/packages/svelte/tests/runtime-xhtml/samples/comment-marker/_config.js b/packages/svelte/tests/runtime-xhtml/samples/comment-marker/_config.js
new file mode 100644
index 0000000000..f47bee71df
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/comment-marker/_config.js
@@ -0,0 +1,3 @@
+import { test } from '../../test';
+
+export default test({});
diff --git a/packages/svelte/tests/runtime-xhtml/samples/comment-marker/main.svelte b/packages/svelte/tests/runtime-xhtml/samples/comment-marker/main.svelte
new file mode 100644
index 0000000000..8dd87ce81e
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/comment-marker/main.svelte
@@ -0,0 +1 @@
+{#each [1,2] as i}{i}{/each}
diff --git a/packages/svelte/tests/runtime-xhtml/samples/is-xhtml/_config.js b/packages/svelte/tests/runtime-xhtml/samples/is-xhtml/_config.js
new file mode 100644
index 0000000000..52dddb4ad7
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/is-xhtml/_config.js
@@ -0,0 +1,8 @@
+import { test } from '../../test';
+
+export default test({
+ mode: ['client'],
+ test({ assert, target }) {
+ assert.htmlEqual(target.innerHTML, `div
`);
+ }
+});
diff --git a/packages/svelte/tests/runtime-xhtml/samples/is-xhtml/main.svelte b/packages/svelte/tests/runtime-xhtml/samples/is-xhtml/main.svelte
new file mode 100644
index 0000000000..27a4378d0f
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/is-xhtml/main.svelte
@@ -0,0 +1,5 @@
+
+{nodeName}
diff --git a/packages/svelte/tests/runtime-xhtml/samples/void-tags/_config.js b/packages/svelte/tests/runtime-xhtml/samples/void-tags/_config.js
new file mode 100644
index 0000000000..f47bee71df
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/void-tags/_config.js
@@ -0,0 +1,3 @@
+import { test } from '../../test';
+
+export default test({});
diff --git a/packages/svelte/tests/runtime-xhtml/samples/void-tags/main.svelte b/packages/svelte/tests/runtime-xhtml/samples/void-tags/main.svelte
new file mode 100644
index 0000000000..08ea2838b3
--- /dev/null
+++ b/packages/svelte/tests/runtime-xhtml/samples/void-tags/main.svelte
@@ -0,0 +1,15 @@
+
+
+
+
+