Description
Describe the bug
If you have a component that creates a bunch of text nodes via an {#each}
loop, on HMR the spaces between those nodes disappear (see video). On page refresh the spaces come back, so this appears to be an HMR problem.
svelte-hmr-issue.mp4
I tested Svelte versions and found that this issue started in svelte@5.0.0-next.97
. Summary of tested versions (✅ means it worked as expected, ❌ means the issue was observed):
- ❌ 5.0.0-next.150
- ❌ 5.0.0-next.100
- ❌ 5.0.0-next.97
- ✅ 5.0.0-next.96
- ✅ 5.0.0-next.95
- ✅ 5.0.0-next.93
- ✅ 5.0.0-next.87
- ✅ 5.0.0-next.75
- ✅ 5.0.0-next.50
- ✅ 4.2.17
It appears that on HMR the text nodes are being replaced such that:
💡 Any text node whose data
was " "
gets replaced with a nullstring ""
Reproduction
You can observe this behavior in the Svelte 5 REPL, but there you can only see it with the spaces removed. For a full reproduction, do the following:
- Create a new SvelteKit application (e.g.
npm create svelte@latest hmr-whitespace
) - Replace the
package.json
contents with the following to ensure the same dependency versions:{ "name": "hmr-whitespace", "version": "0.0.1", "private": true, "scripts": { "dev": "vite dev", "build": "vite build", "preview": "vite preview" }, "devDependencies": { "@sveltejs/adapter-auto": "^3.2.1", "@sveltejs/kit": "^2.5.10", "@sveltejs/vite-plugin-svelte": "^3.1.1", "svelte": "5.0.0-next.97", "vite": "^5.2.12" }, "type": "module" }
- Install deps (
npm install
) - Replace the contents of
hmr-spaces/src/routes/+page.svelte
with:<script> let string = "Where did the spaces go?"; const words = string.split(/( )/); // Note that regex groups in `.split` *keep* the spaces, unlike when there is no group console.log(words); </script> <p> {#each words as word} {word} {/each} </p>
- Run and view the page (
npm run dev
) - Observe that the content looks as expected (the text has spaces)
- In the Chrome console, run
[$('p')]
to inspect the element. Observe that itschildNodes
include Text nodes whosedata
value is a space (" "
)
- In the Chrome console, run
- Edit the value of the
string
variable to trigger HMR - Observe that the text has lost its spaces
- In the Chrome console, run
[$('p')]
to inspect the element. Observe that the Text nodes in itschildNodes
that used to be spaces (" "
) are now null strings (""
).
- In the Chrome console, run
- Refresh the page
- Observe that the spaces have returned
The video above shows what you should observe.
Repeating this test with any Svelte version above 5.0.0-next.97
yields the same outcome. All versions less than 5.0.0-next.97
do NOT yield this outcome and work as expected.
Logs
In the Chrome console, the only log is:
[vite] hot updated: /src/routes/+page.svelte
Similarly, in the Node console:
9:28:45 AM [vite] hmr update /src/routes/+page.svelte
System Info
See the package.json
content listed above for project dependency versions.
Additional system info:
OS: Windows 11 10.0.22631
CPU: (20) x64 12th Gen Intel(R) Core(TM) i7-12700KF
Memory: 34.77 GB / 63.82 GB
Binaries:
Node: 20.11.0 - C:\Program Files\nodejs\node.EXE
npm: 10.2.4 - C:\Program Files\nodejs\npm.CMD
pnpm: 9.2.0 - C:\Program Files\nodejs\pnpm.CMD
Browsers:
Edge: Chromium (125.0.2535.67)
Internet Explorer: 11.0.22621.3527
npmPackages:
svelte: 5.0.0-next.97 => 5.0.0-next.97
Severity
This behavior completely breaks my application