Skip to main content
Svelte Fundamentals
CHAPTER 05 Beginner

Reactivity in Svelte

Updated: May 18, 2026
5 min read

# CHAPTER 5

Reactivity in Svelte

1. Chapter Introduction

Svelte's reactivity is its most celebrated feature. In React, you call setState(). In Vue, you use ref() or reactive(). In Svelte, you simply assign to a variable. That's it. The Svelte compiler detects that a variable is used in the template and generates targeted DOM update code automatically. This chapter fully explains how this magic works.

2. Learning Objectives

  • Understand how Svelte's compiler creates reactive updates.
  • Use reactive assignments to trigger DOM updates.
  • Use reactive declarations ($:) for derived values.
  • Use reactive blocks for side effects.
  • Understand array and object reactivity caveats.

3. How Svelte Reactivity Works

text
12345678910111213141516
Svelte Reactivity Flow:

  let count = 0;
        |
        v
  [ Compiler analyzes which DOM nodes use 'count' ]
        |
        v
  User interaction triggers: count = count + 1
        |
        v
  Compiler-generated update function runs
        |
        v
  ONLY the specific DOM text node updates
        (No full re-render, no virtual DOM diff!)

4. Basic Reactive Assignment

svelte
12345678910111213141516171819202122
<script>
  let count = 0;

  function increment() {
    count = count + 1; // Just an assignment! Svelte handles the DOM update.
  }

  function decrement() {
    count -= 1;
  }

  function reset() {
    count = 0;
  }
</script>

<div class="counter">
  <h1>{count}</h1>
  <button on:click={decrement}>−</button>
  <button on:click={reset}>Reset</button>
  <button on:click={increment}>+</button>
</div>

5. Reactive Declarations $: — Derived Values

Reactive declarations are Svelte's computed properties. They automatically recalculate when their dependencies change:
svelte
12345678910111213141516
<script>
  let celsius = 0;

  // Automatically updates when celsius changes
  $: fahrenheit = (celsius * 9/5) + 32;
  $: kelvin = celsius + 273.15;

  // Reactive condition
  $: isBoiling = celsius >= 100;
  $: tempLabel = isBoiling ? &#039;🔥 Boiling!' : '❄️ Not boiling';
</script>

<h2>Temperature Converter</h2>
<input type="range" min="-50" max="150" bind:value={celsius} />
<p>{celsius}°C = {fahrenheit.toFixed(1)}°F = {kelvin.toFixed(1)}K</p>
<p class:warning={isBoiling}>{tempLabel}</p>

6. Reactive Blocks — Side Effects

A $: block runs whenever any variable inside it changes:
svelte
123456789101112131415161718192021222324252627
<script>
  let searchTerm = &#039;';
  let results = [];

  $: {
    // This block runs every time searchTerm changes
    console.log(&#039;Searching for:', searchTerm);
    if (searchTerm.length >= 2) {
      results = performSearch(searchTerm);
    } else {
      results = [];
    }
  }

  function performSearch(term) {
    // Simulate search
    return [&#039;Apple', 'Banana', 'Cherry']
      .filter(item => item.toLowerCase().includes(term.toLowerCase()));
  }
</script>

<input bind:value={searchTerm} placeholder="Search..." />
<ul>
  {#each results as result}
    <li>{result}</li>
  {/each}
</ul>

7. Array and Object Reactivity — The Assignment Rule

Critical: Svelte only detects reactivity through assignment (=). Array mutations like .push() or .splice() do NOT trigger updates because they don't use =.
svelte
123456789101112131415161718192021222324252627282930
<script>
  let items = [&#039;Apple', 'Banana'];

  function addItemWrong() {
    items.push(&#039;Cherry'); // ❌ Does NOT trigger an update!
  }

  function addItemCorrect() {
    items = [...items, &#039;Cherry']; // ✅ Assignment triggers update!
    // OR:
    // items = items.concat('Cherry');
  }

  // Object mutation
  let user = { name: &#039;Alice', age: 25 };

  function birthday() {
    user.age += 1; // ✅ THIS WORKS! Property assignment triggers reactivity
    // Svelte is smart enough to detect this
  }
</script>

<ul>
  {#each items as item}
    <li>{item}</li>
  {/each}
</ul>
<button on:click={addItemCorrect}>Add Item</button>
<p>{user.name} is {user.age}</p>
<button on:click={birthday}>Happy Birthday!</button>

8. Mini Project: Live Counter App

svelte
12345678910111213141516171819202122232425262728293031323334353637383940414243
<!-- Counter.svelte -->
<script>
  let count = 0;
  let step = 1;
  let history = [];

  $: isPositive = count > 0;
  $: isNegative = count < 0;
  $: statusEmoji = count === 0 ? &#039;😐' : isPositive ? '😊' : '😟';

  function change(amount) {
    count += amount;
    history = [...history, { value: count, time: new Date().toLocaleTimeString() }];
  }

  function reset() {
    count = 0;
    history = [];
  }
</script>

<div class="counter-app">
  <div class="display" class:positive={isPositive} class:negative={isNegative}>
    <span class="emoji">{statusEmoji}</span>
    <span class="value">{count}</span>
  </div>

  <div class="controls">
    <input type="number" bind:value={step} min="1" />
    <button on:click={() => change(-step)}>−{step}</button>
    <button on:click={reset}>Reset</button>
    <button on:click={() => change(step)}>+{step}</button>
  </div>

  {#if history.length > 0}
    <div class="history">
      <h4>History</h4>
      {#each history.slice(-5) as entry}
        <p>{entry.time}: {entry.value}</p>
      {/each}
    </div>
  {/if}
</div>

9. Common Mistakes

  • Array mutations without reassignment: arr.push(item) is the #1 beginner mistake. Always use arr = [...arr, item].
  • Circular reactive declarations: $: a = b + 1; $: b = a + 1; creates an infinite loop. Reactive dependencies must be acyclic.

10. MCQs with Answers

Question 1

How does Svelte know when to update the DOM?

Question 2

Why does array.push(item) NOT trigger a Svelte reactivity update?

Question 3

What is the correct way to add an item to a reactive array?

Question 4

What does $: total = price * quantity create?

Question 5

In $: { console.log(name); }, when does this block run?

Question 6

Does object property assignment trigger reactivity?

Question 7

What happens to an $: reactive declaration when the component is created?

Question 8

Can you have multiple reactive declarations in one component?

Question 9

What would cause a circular reactive dependency?

Question 10

How is Svelte's reactivity simpler than React's useState?

11. Interview Questions

  • Q: Explain how Svelte achieves reactivity without a Virtual DOM.
  • Q: What is the "assignment rule" in Svelte and why does it exist?

12. Summary

Svelte's reactivity model is beautifully simple: assignment triggers updates. The compiler identifies where each variable is used in the template and generates surgical update functions. The $: prefix extends this to derived values and side effects. Understanding the assignment rule (especially for arrays) is the most critical piece of knowledge for writing correct Svelte code.

13. Next Chapter Recommendation

In Chapter 6: Variables and State Management, we explore local component state in depth — how to structure complex state, use nested objects, and manage state across multiple components.

Finish this Chapter

Save your progress on your learning path and prepare for coding interview challenges.

Discussion

Join the discussion

Log in or create a free account to participate.

Sort: ·