Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Svelte 5: ERR_SVELTE_TOO_MANY_UPDATES when updating state #9712

Closed
amit13k opened this issue Nov 30, 2023 · 5 comments
Closed

Svelte 5: ERR_SVELTE_TOO_MANY_UPDATES when updating state #9712

amit13k opened this issue Nov 30, 2023 · 5 comments

Comments

@amit13k
Copy link

amit13k commented Nov 30, 2023

Describe the bug

This code leads to ERR_SVELTE_TOO_MANY_UPDATES,

<script>
let x = $state({
	count: 0
});

$effect(() => {
	x.count = 1;
});
</script>

while this doesn't cause any error,

<script>
let x = $state({
	count: 0
});

$effect(() => {
	x = { count: 1 }
});
</script>

Looks like a reactivity bug.

Reproduction

Svelte 5 REPL with Error

Svelte 5 REPL without Error

Logs

No response

System Info

System:
    OS: macOS 14.2
    CPU: (12) arm64 Apple M2 Pro
    Memory: 269.64 MB / 16.00 GB
    Shell: 5.9 - /bin/zsh
  Binaries:
    Node: 21.2.0 - /opt/homebrew/bin/node
    Yarn: 1.22.21 - /opt/homebrew/bin/yarn
    npm: 10.2.4 - /opt/homebrew/bin/npm
    pnpm: 8.11.0 - ~/Library/pnpm/pnpm
    bun: 1.0.3 - ~/.bun/bin/bun
  Browsers:
    Chrome: 119.0.6045.199
    Chrome Canary: 121.0.6156.2
    Safari: 17.2

Severity

blocking an upgrade

@chainlist
Copy link

As far as I understood $effect, to me, it is not a good practice to reassign values while in an $effect.

Unless you are using untrack to avoid the infiinite update loop.

<script>
   import { untrack } from 'svelte';

   let x= $state({ count: 0 });

  $effect(() => {
    untrack(() => {
       x.count += 1;
   });
  });
</script>

@7nik
Copy link

7nik commented Nov 30, 2023

x.count = 1; is the same as a.b.c.d = 1 - to assign to d, you need to read a, its b and b's c.

Also, use guards:

$effect(() => {
  if (x.count !== 1) {
    x.count = 1;
  }
});

In other cases, turn the used variables into primitives or separate the effect's dependencies and mutated variables

@brunnerh
Copy link
Member

@Rich-Harris
Copy link
Member

This would be fixed by #9685, but we're holding off merging that because we have a more comprehensive update in the works that will change the behaviour around this stuff. We'll open a PR soon

@amit13k
Copy link
Author

amit13k commented Dec 5, 2023

Fixed in svelte@5.0.0-next.18

@amit13k amit13k closed this as completed Dec 5, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants