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: component not updated correctly #11352

Closed
dispatchqueue opened this issue Apr 28, 2024 · 3 comments · Fixed by #11364
Closed

Svelte 5: component not updated correctly #11352

dispatchqueue opened this issue Apr 28, 2024 · 3 comments · Fixed by #11364
Milestone

Comments

@dispatchqueue
Copy link

Describe the bug

When you open the REPL below and click the Next button to proceed to Question B, the number displayed is 1, which is correct. I expect the number to increase each time the Next button is clicked. However, when you click the Next button, the number does not increase.

To make it work correctly, I need to make one of the following changes:

  1. Swap the if and else statements from this:
{#if currentQuestion.type === 'B'}
    <QuestionB bind:question={currentQuestion} />
{:else if currentQuestion.type === 'A'}
    <QuestionA bind:question={currentQuestion} />
{/if}

To this:

{#if currentQuestion.type === 'A'}
    <QuestionA bind:question={currentQuestion} />
{:else if currentQuestion.type === 'B'}
    <QuestionB bind:question={currentQuestion} />
{/if}
  1. Or in QuestionB.svelte, instead of rendering the title using $derived like this:
<script>
  const { question = $bindable() } = $props()
  const title = $derived(`Question B - ${question.option}`)
</script>

<h1>{title}</h1>

<div>Number: {question.number}</div>

Removing $derived and rendering the title directly in the HTML will make it work:

<script>
  const { question = $bindable() } = $props()
</script>

<h1>{`Question B - ${question.option}`}</h1>

<div>Number: {question.number}</div>

Another behavior is that if you remove the question A from the array, the number will be updated correctly:

function newTest() {
    return {
        questions: [
-           newQuestionA(),
            newQuestionB(1, 'Option 1'),
            newQuestionB(2, 'Option 1'),
            newQuestionB(3, 'Option 1'),
            newQuestionB(4, 'Option 1'),
            newQuestionB(5, 'Option 1'),
            newQuestionB(6, 'Option 1')
        ]
    }
  }

Here is the same REPL using Svelte 4, which works well: REPL

Reproduction

REPL

Logs

No response

System Info

N/A

Severity

annoyance

@MotionlessTrain
Copy link

Making currentQuestion a $derived rather than updating via an $effect seems to work too
And if a new derived is made in QuestionB for number, instead of using question.number in the template directly, it also seems to work

@gterras
Copy link

gterras commented Apr 28, 2024

I don't known if this should work but it seems a bit far stretched, from the docs:

In general, $effect is best considered something of an escape hatch — useful for things like analytics and direct DOM manipulation — rather than a tool you should use frequently. In particular, avoid using it to synchronise state. Instead [use $derived].

In addition the bindings don't seem to do anything?

@dispatchqueue
Copy link
Author

I don't known if this should work but it seems a bit far stretched, from the docs:

In general, $effect is best considered something of an escape hatch — useful for things like analytics and direct DOM manipulation — rather than a tool you should use frequently. In particular, avoid using it to synchronise state. Instead [use $derived].

In addition the bindings don't seem to do anything?

I removed $effect as suggested in the docs, but it still doesn't work: REPL

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

Successfully merging a pull request may close this issue.

4 participants