diff --git a/.changeset/tender-apples-repair.md b/.changeset/tender-apples-repair.md
new file mode 100644
index 000000000000..0e600e66241a
--- /dev/null
+++ b/.changeset/tender-apples-repair.md
@@ -0,0 +1,5 @@
+---
+'svelte': patch
+---
+
+fix: put expressions in effects unless known to be static
diff --git a/packages/svelte/src/compiler/phases/2-analyze/visitors/Identifier.js b/packages/svelte/src/compiler/phases/2-analyze/visitors/Identifier.js
index efbbe6cfa287..83ac8000d311 100644
--- a/packages/svelte/src/compiler/phases/2-analyze/visitors/Identifier.js
+++ b/packages/svelte/src/compiler/phases/2-analyze/visitors/Identifier.js
@@ -90,7 +90,8 @@ export function Identifier(node, context) {
if (binding) {
if (context.state.expression) {
context.state.expression.dependencies.add(binding);
- context.state.expression.has_state ||= binding.kind !== 'normal';
+ context.state.expression.has_state ||=
+ !binding.is_function() && !context.state.scope.evaluate(node).is_known;
}
if (
diff --git a/packages/svelte/tests/runtime-runes/samples/reactive-identifier/_config.js b/packages/svelte/tests/runtime-runes/samples/reactive-identifier/_config.js
new file mode 100644
index 000000000000..de59e8c7c7c8
--- /dev/null
+++ b/packages/svelte/tests/runtime-runes/samples/reactive-identifier/_config.js
@@ -0,0 +1,13 @@
+import { flushSync } from '../../../../src/index-client';
+import { test } from '../../test';
+
+export default test({
+ html: ``,
+
+ test({ assert, target }) {
+ const btn = target.querySelector('button');
+
+ flushSync(() => btn?.click());
+ assert.htmlEqual(target.innerHTML, ``);
+ }
+});
diff --git a/packages/svelte/tests/runtime-runes/samples/reactive-identifier/main.svelte b/packages/svelte/tests/runtime-runes/samples/reactive-identifier/main.svelte
new file mode 100644
index 000000000000..aee0b15e1beb
--- /dev/null
+++ b/packages/svelte/tests/runtime-runes/samples/reactive-identifier/main.svelte
@@ -0,0 +1,13 @@
+
+
+