ข้ามไปยังเนื้อหา

State ใน Modules

นักพัฒนา React แชร์ state ข้าม component tree ด้วย Context — createContext, Provider ที่ครอบส่วนหนึ่งของ tree, และ useContext ในทุก consumer ทำงานได้ แต่ต้องการ boilerplate มาก: Provider ต้องครอบทุก consumer และการเพิ่ม shared state ใหม่หมายถึงต้องอัปเดต Provider ด้วย

Svelte 5 แนะนำโมเดลที่เรียบง่ายกว่า: .svelte.ts modules คุณประกาศ $state และ $derived ระดับ module ในไฟล์ .svelte.ts (หรือ .svelte.js) แล้ว export ออกมา จากนั้น import เข้า component ใดก็ได้ Reactivity ทำงานเองโดยอัตโนมัติ — ทุก component ที่อ่านตัวแปรนั้นจะ re-render เมื่อค่าเปลี่ยน ไม่ต้องมี Provider ไม่ต้องมี context object ไม่ต้อง useContext

React
// userStore.ts
import { createContext, useContext, useState } from 'react';
const UserContext = createContext(null);
export function UserProvider({ children }) {
const [user, setUser] = useState(null);
return (
<UserContext.Provider value={{ user, setUser }}>
{children}
</UserContext.Provider>
);
}
export function useUser() {
return useContext(UserContext);
}
// App.tsx — must wrap consumers
<UserProvider>
<Header />
<Main />
</UserProvider>
// Header.tsx
const { user } = useUser();
Svelte
// user.svelte.ts
export let user = $state(null);
export function setUser(next) { user = next; }
// Header.svelte — just import, no Provider needed
<script>
import { user, setUser } from './user.svelte.ts';
</script>
<p>Hello, {user?.name ?? 'Guest'}</p>
<button onclick={() => setUser({ name: 'Ada' })}>Log in</button>
// Main.svelte — same import, same reactive state
<script>
import { user } from './user.svelte.ts';
</script>
{#if user}
<p>Welcome back, {user.name}!</p>
{/if}

ทุก component ที่ import user จาก user.svelte.ts จะ re-render โดยอัตโนมัติเมื่อ user เปลี่ยน เพราะ Svelte compiler มอง $state variables เป็น reactive แม้ในระดับ module scope

.svelte.ts modules ต้องใช้หลายไฟล์ ซึ่ง playground ไม่รองรับ ด้านล่างนี้คือ demo แบบ self-contained ที่ใช้ reactive pattern เดียวกัน — $state และ $derived ประกาศที่ต้น script block จำลองการแชร์ข้ามส่วนต่างๆ ของ UI

ในโปรเจกต์จริง คุณจะย้าย state declarations ไปไว้ในไฟล์ .svelte.ts แล้ว import เข้ามา

extension ไฟล์ใดที่เปิดใช้งาน $state และ $derived ระดับ module scope ใน Svelte 5?
Component import ตัวแปร $state จาก .svelte.ts module เมื่อไหร่ component จะ re-render?
module-level $state แทนที่ React pattern ใด และเอาอะไรออก?