Tanstack Start
Create stan-js store in your app:
import { createScopedStore } from 'stan-js'
export const { StoreProvider, useScopedStore, useStore } = createScopedStore({ user: '', counter: 0,})
Calculate initial values (e.g. fetch some data using Server Functions or get it from search params) and pass that to StoreProvider
:
import { createRootRoute, HeadContent, Outlet, Scripts,} from '@tanstack/react-router'import { createServerFn } from '@tanstack/react-start'import { z } from 'zod'import { fetchUser } from '../data'import globals from '../globals.css?url'import { StoreProvider } from '../store'
const RootComponent = () => { const { user } = Route.useLoaderData() const { counter } = Route.useSearch()
return ( <html> <head> <HeadContent /> </head> <body> <StoreProvider initialValue={{ user, counter }}> <Outlet /> </StoreProvider> <Scripts /> </body> </html> )}
const getUser = createServerFn({ method: 'GET' }).handler(fetchUser)
export const Route = createRootRoute({ head: () => ({ meta: [ { charSet: 'utf-8', }, { name: 'viewport', content: 'width=device-width, initial-scale=1', }, { title: 'TanStack Start Starter', }, ], links: [ { rel: 'stylesheet', href: globals }, ], }), component: RootComponent, loader: async () => { const user = await getUser()
return { user, } }, validateSearch: z.object({ counter: z.number().optional(), }),})
Use useStore
to access the store in your components:
import { createFileRoute } from '@tanstack/react-router'import { Counter } from '../components/Counter'import { useStore } from '../store'
const Home = () => { const { user } = useStore()
return ( <main> <h1> Hello {user}! </h1> <Counter /> </main> )}
export const Route = createFileRoute('/')({ component: Home,})
import { useStore } from '../store'
export const Counter = () => { const { counter, setCounter } = useStore()
return ( <section> <button onClick={() => setCounter(prev => prev - 1)}>-</button> <span>{counter}</span> <button onClick={() => setCounter(prev => prev + 1)}>+</button> </section> )}