Skip to content

$effect doesn’t re-run after changing a $derived value it depends on #14976

@wjainek

Description

@wjainek

Describe the bug

If an $effect indirectly changes a $derived value it depends on, it doesn’t re-run. This is inconsistent with the simpler case where the $effect depends directly on the changed value.

Reproduction
The following code demonstrates the issue. In the diagram, dashed lines represent dependencies, and the dotted line a mutation.

// value --> doubled --> effect
//   ^                     .
//   .                     .
//   .......................

let value   = $state(1);
let doubled = $derived(value * 2);

$effect(() => {
  console.log(doubled);
  value = 10;
});

// Expected output: 2, 20
// Actual output:   2

Expected behavior
After mutating value inside the effect, the effect should be re-run since it depends on doubled, which in turn depends on value. The expected output is two log outputs: 2 followed by 20.

Actual behavior
The effect is only run once, producing a log output of 2.

Comparison case
Contrast this behavior to the simpler case, where the effect depends directly on value. Here, the effect is re-run as expected:

// value --> effect
//   ^         .
//   .         .
//   ...........

let value = $state(1);

$effect(() => {
  console.log(value);
  value = 10;
});

// Expected output: 1, 10
// Actual output:   1, 10

Reproduction

https://svelte.dev/playground/acd432616b63452d923e84109d62a23e?version=5.17.3

Logs

No response

System Info

System:
  OS: macOS 15.1.1
  CPU: (10) arm64 Apple M1 Max
  Memory: 179.77 MB / 64.00 GB
  Shell: 5.9 - /bin/zsh
Binaries:
  Node: 22.9.0 - /opt/homebrew/bin/node
  npm: 10.8.3 - /opt/homebrew/bin/npm
Browsers:
  Chrome: 131.0.6778.265
  Safari: 18.1.1
npmPackages:
  svelte: ^5.15.0 => 5.17.3

Severity

annoyance

Metadata

Metadata

Assignees

Labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions