diff --git a/.changeset/short-chicken-compare.md b/.changeset/short-chicken-compare.md
new file mode 100644
index 000000000000..d0f6c22de4b7
--- /dev/null
+++ b/.changeset/short-chicken-compare.md
@@ -0,0 +1,5 @@
+---
+'svelte': patch
+---
+
+fix: ensure last empty text node correctly hydrates
diff --git a/packages/svelte/src/internal/client/dom/operations.js b/packages/svelte/src/internal/client/dom/operations.js
index 6dfce9ebd320..627bf917eee1 100644
--- a/packages/svelte/src/internal/client/dom/operations.js
+++ b/packages/svelte/src/internal/client/dom/operations.js
@@ -154,8 +154,10 @@ export function first_child(fragment, is_text) {
*/
export function sibling(node, count = 1, is_text = false) {
let next_sibling = hydrating ? hydrate_node : node;
+ var last_sibling;
while (count--) {
+ last_sibling = next_sibling;
next_sibling = /** @type {TemplateNode} */ (get_next_sibling(next_sibling));
}
@@ -163,13 +165,20 @@ export function sibling(node, count = 1, is_text = false) {
return next_sibling;
}
- var type = next_sibling.nodeType;
+ var type = next_sibling?.nodeType;
// if a sibling {expression} is empty during SSR, there might be no
// text node to hydrate — we must therefore create one
if (is_text && type !== 3) {
var text = create_text();
- next_sibling?.before(text);
+ // If the next sibling is `null` and we're handling text then it's because
+ // the SSR content was empty for the text, so we need to generate a new text
+ // node and insert it after the last sibling
+ if (next_sibling === null) {
+ last_sibling?.after(text);
+ } else {
+ next_sibling.before(text);
+ }
set_hydrate_node(text);
return text;
}
diff --git a/packages/svelte/tests/hydration/samples/text-empty-2/_config.js b/packages/svelte/tests/hydration/samples/text-empty-2/_config.js
new file mode 100644
index 000000000000..f47bee71df87
--- /dev/null
+++ b/packages/svelte/tests/hydration/samples/text-empty-2/_config.js
@@ -0,0 +1,3 @@
+import { test } from '../../test';
+
+export default test({});
diff --git a/packages/svelte/tests/hydration/samples/text-empty-2/_expected.html b/packages/svelte/tests/hydration/samples/text-empty-2/_expected.html
new file mode 100644
index 000000000000..ff12f10bfb75
--- /dev/null
+++ b/packages/svelte/tests/hydration/samples/text-empty-2/_expected.html
@@ -0,0 +1 @@
+
diff --git a/packages/svelte/tests/hydration/samples/text-empty-2/main.svelte b/packages/svelte/tests/hydration/samples/text-empty-2/main.svelte
new file mode 100644
index 000000000000..ae1ed05e3a84
--- /dev/null
+++ b/packages/svelte/tests/hydration/samples/text-empty-2/main.svelte
@@ -0,0 +1,7 @@
+
+
+
+ {name}{remaining >= 2 ? ',' : ''}
+