Namespacing / slicing application state alike Redux' combineReducers
See original GitHub issueHey!
I just came across this library, and am quite enthusiastic already š„³
Iāve ditched Redux in the past, only to have returned to adding it back later because of a need for a common-sense global application state instance when using various somewhat-interdependent contexts didnāt work out better than Redux in the first place.
One think I really dislike about Redux, is the ergonomic pain of having to differentiate between synchronous and asynchronous (or otherwise indirect) operations. This always feels like a āfakeā or accidental technically-contrained version of a private/public layered approach. Often, the set of ordinary actions end up kind of like a private store api, and the async actions (or otherwise indirect thunks) end up like the public api.
Zustand seems to nicely eliminate this distinction from it ergonomics, retaining the same general approach but without the ābureaucratic fussā letās say.
const useStore = create((set, get, api) => {
// set up the state layout
const initialState = { ... };
// some internal helpers
const privateFn = (...) => { ... get() ... set(...) ... };
// the public api
const publicFn = (...) => { ... get() ... privateFn(...) ... };
return {
...initialState,
publicFn,
...
};
});
Iām tempted to look into replacing Redux for Zustand in my (medium-scale, web & native) app, but would first need to concoct/add a few tools to be able to transition from what we have now. Up top on that list is the ability to divide the top-level state into somewhat independent āslicesā, e.g. combineReducers
in Redux.
Hereās a little attempt I made at something that would look similar, but maybe be a bit more flexible than a drop-in combineCreators
(which was my first idea):
https://codesandbox.io/s/zustand-combinecreators-ojew5?file=/src/App.tsx
const useStore = create((get, set, api) => {
const counterSlice = namespace("counter", createCounter)(get, set, api);
...
const crossSliceOperation = (...) => { ... };
return {
counter: counterSlice,
crossSliceOperation,
...
};
});
(Also, typing all of this is not super trivial, and probably requires some overloading of SetState
etc.)
What are your thoughts?
Issue Analytics
- State:
- Created 3 years ago
- Reactions:1
- Comments:10 (6 by maintainers)
Top GitHub Comments
Several people seem to be interested in this.
I created a helper package to deal with nested sub-stores: zustand-lens
You can define a sub-store like this:
Here,
set
andget
are identical to zustandās originalcreate((set, get) => )
, but they are scoped to sub-store.This way you can have multiple independent sub-stores which donāt care about parent state shape:
If your sub-stores need each otherās state, just use global
set
andget
functions.