react-state-custom 1.0.27 → 1.0.29
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +61 -12
- package/dist/index.es.js +527 -393
- package/dist/index.es.js.map +1 -1
- package/dist/index.umd.js +4 -4
- package/dist/index.umd.js.map +1 -1
- package/dist/react-state-custom.css +1 -1
- package/dist/state-utils/createAutoCtx.d.ts +2 -1
- package/dist/state-utils/createRootCtx.d.ts +2 -1
- package/dist/state-utils/ctx.d.ts +1 -1
- package/dist/state-utils/paramsToId.d.ts +3 -1
- package/package.json +4 -4
- package/dist/state-utils/useRefValue.d.ts +0 -1
package/README.md
CHANGED
|
@@ -20,8 +20,53 @@ npm install react-state-custom
|
|
|
20
20
|
|
|
21
21
|
React State Custom lets you write state management code that feels natural—because it **is** just React hooks. Use the same hooks you already know (`useState`, `useEffect`, etc.) to create powerful, shared state without learning new paradigms.
|
|
22
22
|
|
|
23
|
+
### When `useState` + `useEffect` Fall Short
|
|
24
|
+
|
|
25
|
+
Even though React hooks are flexible, they start to hurt once state crosses component boundaries:
|
|
26
|
+
|
|
27
|
+
- **Prop drilling & manual providers** – every time state needs to be shared, you create a context, memoize values, and remember to wrap trees.
|
|
28
|
+
- **Coarse-grained re-renders** – updating one property forces every subscriber of that context to render, even if they don't consume the changed field.
|
|
29
|
+
- **Lifecycle bookkeeping** – you manually manage instance lifetimes, clean up effects, and guard against components mounting before providers.
|
|
30
|
+
- **Zero visibility** – there's no built-in way to inspect shared state, throttle noisy updates, or keep debugging breadcrumbs.
|
|
31
|
+
|
|
32
|
+
React State Custom keeps your favorite hooks but layers on automatic context lifecycles, selective subscriptions, and built-in tooling so you can stay productive as your app grows.
|
|
33
|
+
|
|
23
34
|
## ⚡ Quick Example
|
|
24
35
|
|
|
36
|
+
### Without React State Custom (manual context plumbing)
|
|
37
|
+
|
|
38
|
+
```typescript
|
|
39
|
+
const CounterContext = createContext<{
|
|
40
|
+
count: number;
|
|
41
|
+
increment: () => void;
|
|
42
|
+
decrement: () => void;
|
|
43
|
+
} | null>(null);
|
|
44
|
+
|
|
45
|
+
function CounterProvider({ children }: { children: React.ReactNode }) {
|
|
46
|
+
const [count, setCount] = useState(0);
|
|
47
|
+
const value = useMemo(
|
|
48
|
+
() => ({
|
|
49
|
+
count,
|
|
50
|
+
increment: () => setCount(c => c + 1),
|
|
51
|
+
decrement: () => setCount(c => c - 1),
|
|
52
|
+
}),
|
|
53
|
+
[count]
|
|
54
|
+
);
|
|
55
|
+
|
|
56
|
+
return <CounterContext.Provider value={value}>{children}</CounterContext.Provider>;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
function useCounter() {
|
|
60
|
+
const ctx = useContext(CounterContext);
|
|
61
|
+
if (!ctx) throw new Error('CounterProvider missing');
|
|
62
|
+
return ctx;
|
|
63
|
+
}
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
Every consumer re-renders whenever anything in `value` changes, you have to remember to wrap parts of the tree with `CounterProvider`, and tearing this pattern down for parameterized instances gets messy fast.
|
|
67
|
+
|
|
68
|
+
### With React State Custom (hook-first store)
|
|
69
|
+
|
|
25
70
|
```typescript
|
|
26
71
|
import { createRootCtx, createAutoCtx, useQuickSubscribe, AutoRootCtx } from 'react-state-custom';
|
|
27
72
|
|
|
@@ -64,6 +109,8 @@ function Counter() {
|
|
|
64
109
|
|
|
65
110
|
> ℹ️ `AutoRootCtx` accepts optional `Wrapper` and `debugging` props. Pass an ErrorBoundary-like component through `Wrapper` to isolate failures, or set `debugging` to `true` to render raw state snapshots in the DOM (handy alongside React DevTools when tracking updates).
|
|
66
111
|
|
|
112
|
+
`useQuickSubscribe` keeps `Counter` focused on `count`, so even if this context grows with more fields later, the component only re-renders when `count` changes.
|
|
113
|
+
|
|
67
114
|
**That's it!** No reducers, no actions, no providers to wrap—just hooks.
|
|
68
115
|
|
|
69
116
|
## 🎯 Key Features
|
|
@@ -104,18 +151,18 @@ Full type inference and type safety throughout. Your IDE knows exactly what's in
|
|
|
104
151
|
### 5. **Tiny Bundle Size**
|
|
105
152
|
~10KB gzipped. No dependencies except React.
|
|
106
153
|
|
|
107
|
-
## 🆚 Comparison with Redux & Zustand
|
|
154
|
+
## 🆚 Comparison with Hooks, Redux & Zustand
|
|
108
155
|
|
|
109
|
-
| Feature | React State Custom | Redux | Zustand |
|
|
110
|
-
|
|
111
|
-
| **Bundle Size** | ~10KB | ~50KB (with toolkit) | ~1KB |
|
|
112
|
-
| **Learning Curve** | ✅ Minimal (just hooks) | ❌ High (actions, reducers, middleware) | ✅ Low |
|
|
113
|
-
| **Boilerplate** | ✅ None | ❌ Heavy | ✅ Minimal |
|
|
114
|
-
| **Type Safety** | ✅ Full inference | ⚠️ Requires setup | ✅ Good |
|
|
115
|
-
| **Selective Re-renders** | ✅ Built-in | ⚠️ Requires selectors | ✅ Built-in |
|
|
116
|
-
| **DevTools** | ✅ Built-in UI | ✅ Redux DevTools | ✅ DevTools support |
|
|
117
|
-
| **Async Support** | ✅ Native (hooks) | ⚠️ Requires middleware | ✅ Native |
|
|
118
|
-
| **Context Composition** | ✅ Automatic | ❌ Manual | ⚠️ Manual store combination |
|
|
156
|
+
| Feature | React State Custom | Plain Hooks (Context) | Redux | Zustand |
|
|
157
|
+
|---------|-------------------|-----------------------|-------|---------|
|
|
158
|
+
| **Bundle Size** | ~10KB | 0KB (just React) | ~50KB (with toolkit) | ~1KB |
|
|
159
|
+
| **Learning Curve** | ✅ Minimal (just hooks) | ⚠️ Familiar APIs, but patterns are DIY | ❌ High (actions, reducers, middleware) | ✅ Low |
|
|
160
|
+
| **Boilerplate** | ✅ None | ❌ Manual providers + prop drilling | ❌ Heavy | ✅ Minimal |
|
|
161
|
+
| **Type Safety** | ✅ Full inference | ⚠️ Custom per-context typing | ⚠️ Requires setup | ✅ Good |
|
|
162
|
+
| **Selective Re-renders** | ✅ Built-in | ❌ Context update = every consumer renders | ⚠️ Requires selectors | ✅ Built-in |
|
|
163
|
+
| **DevTools** | ✅ Built-in UI | ❌ None | ✅ Redux DevTools | ✅ DevTools support |
|
|
164
|
+
| **Async Support** | ✅ Native (hooks) | ✅ Native (hooks) | ⚠️ Requires middleware | ✅ Native |
|
|
165
|
+
| **Context Composition** | ✅ Automatic | ❌ Manual provider trees | ❌ Manual | ⚠️ Manual store combination |
|
|
119
166
|
|
|
120
167
|
### When to Use React State Custom
|
|
121
168
|
|
|
@@ -269,6 +316,8 @@ function App() {
|
|
|
269
316
|
}
|
|
270
317
|
```
|
|
271
318
|
|
|
319
|
+
The toggle reveals a bottom-docked inspector that now uses resizable split panes powered by `@uiw/react-split`. Drag the gutter to adjust how much space the context list or detail view occupies while keeping your application visible above.
|
|
320
|
+
|
|
272
321
|
**Custom data viewer with rich object visualization:**
|
|
273
322
|
```typescript
|
|
274
323
|
import { DataViewComponent } from 'react-state-custom';
|
|
@@ -405,4 +454,4 @@ MIT License - feel free to use in any project.
|
|
|
405
454
|
|
|
406
455
|
---
|
|
407
456
|
|
|
408
|
-
**Made with ❤️ for developers who love React hooks**
|
|
457
|
+
**Made with ❤️ for developers who love React hooks**
|