Under The Hood
frontend svelte Svelte 5 (stores still supported alongside runes)

Svelte Store Contract: subscribe() & set() with $ Auto-Subscription

Last updated
Prerequisites:
Svelte basics and reactivity concepts
Understanding of subscriptions and unsubscribing
  • svelte
  • stores
  • subscribe
  • contract
  • reactivity
  • writable

Read at your depth

The practical view

A Svelte store is any object with a subscribe method: { subscribe(callback): () => void }. That's the contract. writable() creates a store with set() and update(): const count = writable(0); count.set(1); count.update(n => n + 1);. To read a store's value in a template use the $ prefix: {$count}. The $ prefix auto-subscribes in templates and in .svelte files (it compiles to subscribe/unsubscribe). Outside components (plain .ts), call count.subscribe(v => ...) and keep the returned unsubscribe function. readable(), derived() create read-only and derived stores.

The same idea in other frameworks

react equivalent
Context + useSyncExternalStore is the React analogue of the subscribe contract.

Legacy vs modern

Manual subscribe/unsubscribe vs the $ auto-subscription

In plain JS you must subscribe and call the returned unsubscribe; in Svelte templates the $ prefix handles the full lifecycle automatically.

before → after
Manual subscription outside components
const unsub = count.subscribe(v => { console.log(v); }); // ❌ OLD: must remember to unsubscribe
Template $ auto-subscription
<p>{$count}</p> // ✅ NEW: compiler handles subscribe + unsubscribe lifecycle

Interview gotchas

Context

This tests whether you understand the minimal interop contract — interviewers want to confirm you know that ANY object with subscribe is a store, which is what makes stores extensible and testable.

The mechanical answer

The store contract is: an object with a subscribe method taking a callback and returning an unsubscribe function. That's it. writable/readable/derived are built-in implementations, but any object satisfying the contract is a valid store — which means third-party stores, mocks, and even streams wrapped with a subscribe method interoperate seamlessly with Svelte's $ sugar. The subscribe callback receives the current value immediately upon subscription (synchronous initial emission), then on every subsequent change. The returned unsubscribe function must remove the subscriber. This minimal contract is what allows Svelte to treat stores uniformly: the compiler's $ transformation only depends on subscribe existing.

Trap

The naive answer is 'a store is a writable object'. The contract is just subscribe; writable adds set/update on top. Another trap: assuming subscription is lazy — the callback fires immediately with the current value on subscribe, so code must handle that initial emission. Candidates who can define the contract precisely and mention the synchronous initial call show real understanding.

Under The Hood — a multi-depth technical interview hub.

Third-party licenses Press ⌘ K to search.