zustand-devtool
v0.1.3
Published
Zero-config devtool for Zustand — script tag, auto-discovers stores
Readme
zustand-devtool
Zero-config devtool for Zustand — drop in a <script> tag, get immediate insight into your stores.
No app changes required. Auto-discovers Zustand stores via React Fiber traversal.
Features
- Auto-discovery — finds Zustand stores by walking the React Fiber tree. No middleware required.
- Floating panel — draggable, collapsible panel with a live JSON tree view of the selected store's state. Injected via Shadow DOM to prevent CSS conflicts.
- Console logging — logs state diffs and component re-renders attributed to store changes.
- DOM overlay — flashes a colored border on components that re-rendered due to a store change.
- Store switcher — tabs (≤4 stores) or dropdown (>4 stores) to switch between discovered stores.
Usage
Script tag (recommended)
Add before your app's <script> tag:
<script src="https://unpkg.com/zustand-devtool/dist/zustand-devtool.js"></script>Remove the tag for production — the devtool has zero impact when the tag is absent.
Optional: named store middleware
For stores that haven't rendered yet (e.g. background stores), register them with a display name:
import { devtool } from 'zustand-devtool/middleware'
import { create } from 'zustand'
const useCartStore = create(
devtool(
(set) => ({ count: 0, increment: () => set((s) => ({ count: s.count + 1 })) }),
{ name: 'CartStore' }
)
)The middleware is a no-op in production (when the script tag is absent).
Console output
State change:
[zustand-devtool] CartStore changed
diff → { count: { from: 1, to: 2 } }
before → { count: 1, label: 'items' }
after → { count: 2, label: 'items' }Component re-render:
[zustand-devtool] <Counter> re-rendered (CartStore · count: 1 → 2)Known limitations
- Any
useSyncExternalStoreconsumer (SWR, React Query, Jotai, etc.) will be auto-discovered, not just Zustand. - Stores that have never caused a component to render will not be auto-discovered. Use the middleware as a fallback.
- Tested against Zustand v4 and v5. React 18+ required.
Tech stack
| Concern | Choice |
|---|---|
| UI | Preact (~3KB gz) — can't bundle React into a React devtool |
| Build | Vite — IIFE for script tag, ESM for middleware |
| Language | TypeScript |
| Styling | Plain <style> in Shadow DOM |
Development
bun install
bun test # run all tests
bun run build # build dist/zustand-devtool.js + dist/middleware.js