SolidJS Advanced: Stores, Resources & SolidStart
createStore for Nested State
import { createStore, produce } from 'solid-js/store'
const [state, setState] = createStore({
user: { name: '', age: 0 },
items: [] as string[],
})
// Fine-grained update -- only the name property triggers reactivity,
// not the whole user object
setState('user', 'name', 'Alice')
// produce() allows Immer-style draft mutation syntax while Solid
// still applies the update correctly through its reactive internals
setState(produce((s) => {
s.items.push('new item')
}))createResource & Suspense
import { createResource, Suspense } from 'solid-js'
function UserProfile(props: { userId: () => string }) {
// Automatically tracks loading/error state, and re-fetches
// whenever the userId signal it depends on changes
const [user] = createResource(props.userId, fetchUser)
return <div>{user()?.name}</div>
}
// Suspense coordinates loading state across ALL resources in its
// subtree -- shows fallback until every nested resource resolves
<Suspense fallback={<Spinner />}>
<UserProfile userId={() => currentUserId()} />
</Suspense>batch() for Grouped Updates
import { batch } from 'solid-js'
// Without batch, an effect reading both firstName and lastName
// could run twice (once per individual set call)
batch(() => {
setFirstName('Jane')
setLastName('Doe')
})
// Dependent effects/memos now run only ONCE, seeing the final stateonCleanup
import { onCleanup, createEffect } from 'solid-js'
createEffect(() => {
const id = setInterval(() => console.log('tick'), 1000)
// Runs when this reactive scope is disposed (e.g. component
// unmounts) -- prevents the interval from leaking
onCleanup(() => clearInterval(id))
})SolidStart
SolidStart is Solid's official full-stack meta-framework, providing file-based routing, server-side rendering, and data-loading conventions on top of Solid core -- filling the same role Next.js does for React or SvelteKit does for Svelte.
Keep your own version of these notes — editable, searchable, and organised by your stack.
Start free