@feiyeyuji/simple-nobody-state 0.1.0

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 ADDED
@@ -0,0 +1,179 @@
1
+ # simple-nobody-state
2
+
3
+ `simple-nobody-state` is a small TypeScript-first state toolkit built on top of Zustand. It adds global singleton stores, provider-scoped dependency injection stores, component-local stores, memoized selectors, batch dispatching, strict shallow freezing, and typed helpers for composing and mixing stores.
4
+
5
+ ## Install
6
+
7
+ ```bash
8
+ npm install simple-nobody-state zustand proxy-memoize
9
+ ```
10
+
11
+ React is a peer dependency and should be `>=18`.
12
+
13
+ ## Global Store
14
+
15
+ ```ts
16
+ import { createStore } from "simple-nobody-state";
17
+
18
+ export const counterStore = createStore(
19
+ () => ({
20
+ state: { count: 0 },
21
+ meta: { name: "counter" },
22
+ selectors: {
23
+ double: (state: { count: number }) => state.count * 2,
24
+ },
25
+ actions: {
26
+ inc: (ctx, amount: number = 1) => {
27
+ ctx.setState((state: { count: number }) => ({
28
+ count: state.count + amount,
29
+ }));
30
+ },
31
+ },
32
+ }),
33
+ {
34
+ storeType: "globalStore",
35
+ batch: true,
36
+ strict: true,
37
+ devtools: true,
38
+ },
39
+ );
40
+
41
+ counterStore.dispatch("inc", 2);
42
+ counterStore.actions.inc(1);
43
+ counterStore.subscribe((state) => console.log(state.count));
44
+ ```
45
+
46
+ In React:
47
+
48
+ ```tsx
49
+ function Counter() {
50
+ const count = counterStore.useState((state) => state.count);
51
+ const actions = counterStore.useActions();
52
+
53
+ return <button onClick={() => actions.inc()}>{count}</button>;
54
+ }
55
+ ```
56
+
57
+ Global stores expose:
58
+
59
+ - Hooks: `useState`, `useStateRef`, `useActions`
60
+ - Getters: `state`, `selectors`, `meta`, `actions`
61
+ - Methods: `getState`, `dispatch`, `batchDispatch`, `subscribe`, `destroy`
62
+ - Raw Zustand instance: `store[ZUSTAND]`
63
+
64
+ ## Provider Store
65
+
66
+ ```tsx
67
+ import { createStore, stateEffect } from "simple-nobody-state";
68
+
69
+ const userStore = createStore(
70
+ () => ({
71
+ state: { name: "Ada" },
72
+ actions: {
73
+ rename: (ctx, name: string) => ctx.setState({ name }),
74
+ },
75
+ hooks: {
76
+ created: (store) => console.log("created", store.meta),
77
+ destroy: () => console.log("destroyed"),
78
+ },
79
+ }),
80
+ { storeType: "providerStore" },
81
+ );
82
+
83
+ function User() {
84
+ const name = userStore.useState((state) => state.name);
85
+ const actions = userStore.useActions();
86
+
87
+ return <button onClick={() => actions.rename("Grace")}>{name}</button>;
88
+ }
89
+
90
+ function App() {
91
+ return (
92
+ <userStore.Provider
93
+ storeKey="profile"
94
+ effect={stateEffect({ name: "Ada" })}
95
+ >
96
+ <User />
97
+ </userStore.Provider>
98
+ );
99
+ }
100
+ ```
101
+
102
+ Provider stores expose `Provider`, `useState`, `useStateRef`, `useActions`, `useInstance`, `useLocker`, and `getInstance`.
103
+
104
+ The `storeKey` controls sharing. Providers with the same key share one instance. Providers without a key create isolated instances. `useLocker(storeKey)` keeps a keyed instance alive after its Provider unmounts until the locker unmounts.
105
+
106
+ ## stateEffect
107
+
108
+ `stateEffect` is exported at the top level. It turns a partial state object into a Provider effect tuple:
109
+
110
+ ```ts
111
+ const effect = stateEffect({ count: 1 });
112
+ // [Object.entries({ count: 1 }).flat(), updater]
113
+ ```
114
+
115
+ Provider runs the updater inside `useEffect` with dependencies derived from the flattened tuple plus `storeKey`, so external props can synchronize into internal store state.
116
+
117
+ ## Component Store
118
+
119
+ `useStore` creates a component-local store. It is bound to the component lifecycle and is destroyed on unmount.
120
+
121
+ ```tsx
122
+ import { useStore } from "simple-nobody-state";
123
+
124
+ function LocalCounter() {
125
+ const store = useStore(() => ({
126
+ state: { count: 0 },
127
+ actions: {
128
+ inc: (ctx) =>
129
+ ctx.setState((state: { count: number }) => ({
130
+ count: state.count + 1,
131
+ })),
132
+ },
133
+ }));
134
+ const count = store.useState((state) => state.count);
135
+ const actions = store.useActions();
136
+
137
+ return <button onClick={() => actions.inc()}>{count}</button>;
138
+ }
139
+ ```
140
+
141
+ There is no `useLocal` alias.
142
+
143
+ ## Mixin And Compose
144
+
145
+ `mixin` combines definition factories and rejects duplicate state/action/selector keys. Metadata is shallow-merged and lifecycle hooks run in order.
146
+
147
+ ```ts
148
+ const mixed = mixin(sliceA, sliceB);
149
+ const store = createStore(mixed, { storeType: "globalStore" });
150
+ ```
151
+
152
+ `composeStore` groups global and provider stores behind one `ComposeProvider` and namespace-based hooks.
153
+
154
+ ```tsx
155
+ const composed = composeStore({ counter: counterStore, user: userStore });
156
+
157
+ function Page() {
158
+ const count = composed.useComposeState("counter", (state) => state.count);
159
+ const userActions = composed.useComposeActions("user");
160
+ return <button onClick={() => userActions.rename("Grace")}>{count}</button>;
161
+ }
162
+
163
+ function App() {
164
+ return (
165
+ <composed.ComposeProvider providers={{ user: { storeKey: "user" } }}>
166
+ <Page />
167
+ </composed.ComposeProvider>
168
+ );
169
+ }
170
+ ```
171
+
172
+ ## Scripts
173
+
174
+ ```bash
175
+ npm run typecheck
176
+ npm run build
177
+ npm test
178
+ ```
179
+
@@ -0,0 +1,24 @@
1
+ import * as React from "react";
2
+ import type { AnyStore, EqualityFn, GlobalStore, ProviderProps, ProviderStore } from "./types.js";
3
+ type StoreRecord = Record<string, AnyStore>;
4
+ type Namespace<TStores extends StoreRecord> = Extract<keyof TStores, string>;
5
+ type StateOf<TStore> = TStore extends GlobalStore<infer TState, any, any, any> ? TState : TStore extends ProviderStore<infer TState, any, any, any> ? TState : never;
6
+ type ActionsOf<TStore> = TStore extends {
7
+ useActions: () => infer TActions;
8
+ } ? TActions : never;
9
+ type InstanceOf<TStore> = TStore extends ProviderStore<any, any, any, any> ? ReturnType<TStore["useInstance"]> : TStore extends GlobalStore<any, any, any, any> ? TStore : never;
10
+ type ComposeProviderConfig<TStores extends StoreRecord> = Partial<{
11
+ [K in Namespace<TStores>]: TStores[K] extends ProviderStore<infer TState, any, any, any> ? Omit<ProviderProps<TState>, "children"> : never;
12
+ }>;
13
+ export declare function composeStore<const TStores extends StoreRecord>(stores: TStores): {
14
+ ComposeProvider: ({ children, providers, }: {
15
+ children?: React.ReactNode;
16
+ providers?: ComposeProviderConfig<TStores>;
17
+ }) => React.ReactNode;
18
+ useComposeState: <K extends Namespace<TStores>, TSelected = StateOf<TStores[K]>>(namespace: K, selector?: (state: StateOf<TStores[K]>) => TSelected, equality?: EqualityFn<TSelected>) => any;
19
+ useComposeActions: <K extends Namespace<TStores>>(namespace: K) => ActionsOf<TStores[K]>;
20
+ useComposeStore: <K extends Namespace<TStores>>(namespace: K) => InstanceOf<TStores[K]>;
21
+ useComposeSelector: <K extends Namespace<TStores>, TSelector extends string>(namespace: K, selectorName: TSelector) => any;
22
+ };
23
+ export {};
24
+ //# sourceMappingURL=compose-store.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compose-store.d.ts","sourceRoot":"","sources":["../src/lib/compose-store.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAE/B,OAAO,KAAK,EACV,QAAQ,EACR,UAAU,EACV,WAAW,EACX,aAAa,EAEb,aAAa,EAEd,MAAM,YAAY,CAAC;AAEpB,KAAK,WAAW,GAAG,MAAM,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;AAC5C,KAAK,SAAS,CAAC,OAAO,SAAS,WAAW,IAAI,OAAO,CAAC,MAAM,OAAO,EAAE,MAAM,CAAC,CAAC;AAE7E,KAAK,OAAO,CAAC,MAAM,IAAI,MAAM,SAAS,WAAW,CAAC,MAAM,MAAM,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,GAC1E,MAAM,GACN,MAAM,SAAS,aAAa,CAAC,MAAM,MAAM,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,GACvD,MAAM,GACN,KAAK,CAAC;AAEZ,KAAK,SAAS,CAAC,MAAM,IAAI,MAAM,SAAS;IACtC,UAAU,EAAE,MAAM,MAAM,QAAQ,CAAC;CAClC,GACG,QAAQ,GACR,KAAK,CAAC;AAEV,KAAK,UAAU,CAAC,MAAM,IAAI,MAAM,SAAS,aAAa,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,GACtE,UAAU,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,GACjC,MAAM,SAAS,WAAW,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,GAC5C,MAAM,GACN,KAAK,CAAC;AAEZ,KAAK,qBAAqB,CAAC,OAAO,SAAS,WAAW,IAAI,OAAO,CAAC;KAC/D,CAAC,IAAI,SAAS,CAAC,OAAO,CAAC,GAAG,OAAO,CAAC,CAAC,CAAC,SAAS,aAAa,CAAC,MAAM,MAAM,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,GACpF,IAAI,CAAC,aAAa,CAAC,MAAM,CAAC,EAAE,UAAU,CAAC,GACvC,KAAK;CACV,CAAC,CAAC;AAEH,wBAAgB,YAAY,CAAC,KAAK,CAAC,OAAO,SAAS,WAAW,EAC5D,MAAM,EAAE,OAAO;gDAOZ;QACD,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;QAC3B,SAAS,CAAC,EAAE,qBAAqB,CAAC,OAAO,CAAC,CAAC;KAC5C;sBAmBwB,CAAC,SAAS,SAAS,CAAC,OAAO,CAAC,EAAE,SAAS,mCACnD,CAAC,aACD,CAAC,KAAK,EAAE,OAAO,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,KAAK,SAAS,aACzC,UAAU,CAAC,SAAS,CAAC;wBAQP,CAAC,SAAS,SAAS,CAAC,OAAO,CAAC,aAC1C,CAAC,KACX,SAAS,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC;sBAEC,CAAC,SAAS,SAAS,CAAC,OAAO,CAAC,aACxC,CAAC,KACX,UAAU,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC;yBASG,CAAC,SAAS,SAAS,CAAC,OAAO,CAAC,EAAE,SAAS,SAAS,MAAM,aACrE,CAAC,gBACE,SAAS;EAa1B"}
@@ -0,0 +1,43 @@
1
+ import * as React from "react";
2
+ import { STORE_KIND } from "./constants.js";
3
+ export function composeStore(stores) {
4
+ const entries = Object.entries(stores);
5
+ const ComposeProvider = ({ children, providers, }) => {
6
+ return entries
7
+ .slice()
8
+ .reverse()
9
+ .reduce((node, [namespace, store]) => {
10
+ if (store[STORE_KIND] !== "providerStore") {
11
+ return node;
12
+ }
13
+ const Provider = store.Provider;
14
+ const props = (providers?.[namespace] ?? {});
15
+ return React.createElement(Provider, props, node);
16
+ }, children);
17
+ };
18
+ const useComposeState = (namespace, selector, equality) => {
19
+ const store = stores[namespace];
20
+ return selector
21
+ ? store.useState(selector, equality)
22
+ : store.useState();
23
+ };
24
+ const useComposeActions = (namespace) => stores[namespace].useActions();
25
+ const useComposeStore = (namespace) => {
26
+ const store = stores[namespace];
27
+ if (store[STORE_KIND] === "providerStore") {
28
+ return store.useInstance();
29
+ }
30
+ return store;
31
+ };
32
+ const useComposeSelector = (namespace, selectorName) => {
33
+ const instance = useComposeStore(namespace);
34
+ return instance.useState(() => instance.selectors[selectorName]);
35
+ };
36
+ return {
37
+ ComposeProvider,
38
+ useComposeState,
39
+ useComposeActions,
40
+ useComposeStore,
41
+ useComposeSelector,
42
+ };
43
+ }
@@ -0,0 +1,3 @@
1
+ export declare const ZUSTAND: unique symbol;
2
+ export declare const STORE_KIND: unique symbol;
3
+ //# sourceMappingURL=constants.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../src/lib/constants.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,OAAO,EAAE,OAAO,MAA0B,CAAC;AAExD,eAAO,MAAM,UAAU,EAAE,OAAO,MAA2C,CAAC"}
@@ -0,0 +1,2 @@
1
+ export const ZUSTAND = Symbol("zustand");
2
+ export const STORE_KIND = Symbol("simple-nobody-state.kind");
@@ -0,0 +1,5 @@
1
+ import type { CreateStoreOptions, GlobalStore, ProviderStore, StoreActionDefinitions, StoreDefinitionFactory, StoreKey, StoreMeta, StoreSelectorDefinitions } from "./types.js";
2
+ export declare function createStore<TState extends object, TActions extends StoreActionDefinitions = {}, TSelectors extends StoreSelectorDefinitions<TState> = {}, TMeta extends StoreMeta = {}>(definition: StoreDefinitionFactory<TState, TActions, TSelectors, TMeta>, options: CreateStoreOptions<"globalStore">): GlobalStore<TState, TActions, TSelectors, TMeta>;
3
+ export declare function createStore<TState extends object, TActions extends StoreActionDefinitions = {}, TSelectors extends StoreSelectorDefinitions<TState> = {}, TMeta extends StoreMeta = {}>(definition: StoreDefinitionFactory<TState, TActions, TSelectors, TMeta>, options: CreateStoreOptions<"providerStore">): ProviderStore<TState, TActions, TSelectors, TMeta>;
4
+ export declare function useLocker<TState extends object, TActions extends StoreActionDefinitions, TSelectors extends StoreSelectorDefinitions<TState>, TMeta extends StoreMeta>(store: ProviderStore<TState, TActions, TSelectors, TMeta>, storeKey?: StoreKey): import("./types.js").StoreInstance<TState, TActions, TSelectors, TMeta>;
5
+ //# sourceMappingURL=create-store.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"create-store.d.ts","sourceRoot":"","sources":["../src/lib/create-store.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAEV,kBAAkB,EAElB,WAAW,EAEX,aAAa,EAEb,sBAAsB,EACtB,sBAAsB,EACtB,QAAQ,EACR,SAAS,EACT,wBAAwB,EACzB,MAAM,YAAY,CAAC;AAcpB,wBAAgB,WAAW,CACzB,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,GAAG,EAAE,EAC5C,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GAAG,EAAE,EACxD,KAAK,SAAS,SAAS,GAAG,EAAE,EAE5B,UAAU,EAAE,sBAAsB,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,EACvE,OAAO,EAAE,kBAAkB,CAAC,aAAa,CAAC,GACzC,WAAW,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,CAAC;AAEpD,wBAAgB,WAAW,CACzB,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,GAAG,EAAE,EAC5C,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GAAG,EAAE,EACxD,KAAK,SAAS,SAAS,GAAG,EAAE,EAE5B,UAAU,EAAE,sBAAsB,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,EACvE,OAAO,EAAE,kBAAkB,CAAC,eAAe,CAAC,GAC3C,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,CAAC;AAgNtD,wBAAgB,SAAS,CACvB,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,EACvC,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,EACnD,KAAK,SAAS,SAAS,EAEvB,KAAK,EAAE,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,EACzD,QAAQ,CAAC,EAAE,QAAQ,2EAGpB"}
@@ -0,0 +1,134 @@
1
+ import * as React from "react";
2
+ import { STORE_KIND } from "./constants.js";
3
+ import { createRuntimeStore } from "./runtime.js";
4
+ export function createStore(definition, options) {
5
+ if (options.storeType === "globalStore") {
6
+ return createGlobalStore(definition, options);
7
+ }
8
+ return createProviderStore(definition, options);
9
+ }
10
+ function createGlobalStore(definition, options) {
11
+ const instance = createRuntimeStore(definition, options);
12
+ return Object.defineProperty(instance, STORE_KIND, {
13
+ value: "globalStore",
14
+ enumerable: false,
15
+ });
16
+ }
17
+ function createProviderStore(definition, options) {
18
+ const Context = React.createContext(null);
19
+ const registry = new Map();
20
+ const entries = new WeakMap();
21
+ const createEntry = (key) => {
22
+ const instance = createRuntimeStore(definition, options);
23
+ const entry = {
24
+ instance,
25
+ key,
26
+ locks: 0,
27
+ refs: 0,
28
+ };
29
+ entries.set(instance, entry);
30
+ return entry;
31
+ };
32
+ const getOrCreateEntry = (key) => {
33
+ const existing = registry.get(key);
34
+ if (existing) {
35
+ return existing;
36
+ }
37
+ const entry = createEntry(key);
38
+ registry.set(key, entry);
39
+ return entry;
40
+ };
41
+ const cleanup = (entry) => {
42
+ if (entry.refs > 0 || entry.locks > 0 || entry.instance.__isDestroyed()) {
43
+ return;
44
+ }
45
+ entry.instance.destroy();
46
+ if (entry.key !== undefined) {
47
+ registry.delete(entry.key);
48
+ }
49
+ };
50
+ const retain = (entry) => {
51
+ entry.refs += 1;
52
+ if (entry.refs === 1) {
53
+ entry.instance.__mount();
54
+ }
55
+ };
56
+ const release = (entry) => {
57
+ entry.refs = Math.max(0, entry.refs - 1);
58
+ if (entry.refs === 0) {
59
+ entry.instance.__unmount();
60
+ cleanup(entry);
61
+ }
62
+ };
63
+ const lock = (entry) => {
64
+ entry.locks += 1;
65
+ };
66
+ const unlock = (entry) => {
67
+ entry.locks = Math.max(0, entry.locks - 1);
68
+ cleanup(entry);
69
+ };
70
+ const useInstance = () => {
71
+ const instance = React.useContext(Context);
72
+ if (!instance) {
73
+ throw new Error("Provider store hook must be used under its Provider.");
74
+ }
75
+ return instance;
76
+ };
77
+ const Provider = ({ children, storeKey, effect, }) => {
78
+ const entry = React.useMemo(() => storeKey === undefined ? createEntry(undefined) : getOrCreateEntry(storeKey), [storeKey]);
79
+ React.useEffect(() => {
80
+ retain(entry);
81
+ return () => release(entry);
82
+ }, [entry]);
83
+ const effectDeps = effect?.[0] ?? [];
84
+ React.useEffect(() => {
85
+ if (effect) {
86
+ effect[1](entry.instance, effect[0]);
87
+ }
88
+ }, [entry.instance, storeKey, ...effectDeps]);
89
+ return React.createElement(Context.Provider, { value: entry.instance }, children);
90
+ };
91
+ const providerStore = {
92
+ [STORE_KIND]: "providerStore",
93
+ Provider,
94
+ useState: ((selector, equality) => {
95
+ const instance = useInstance();
96
+ return selector
97
+ ? instance.useState(selector, equality)
98
+ : instance.useState();
99
+ }),
100
+ useStateRef: ((selector) => {
101
+ const instance = useInstance();
102
+ return selector ? instance.useStateRef(selector) : instance.useStateRef();
103
+ }),
104
+ useActions: () => {
105
+ const instance = useInstance();
106
+ return instance.useActions();
107
+ },
108
+ useInstance,
109
+ useLocker: (storeKey) => {
110
+ const contextInstance = React.useContext(Context);
111
+ const keyedEntry = React.useMemo(() => (storeKey === undefined ? undefined : getOrCreateEntry(storeKey)), [storeKey]);
112
+ const entry = keyedEntry ??
113
+ (contextInstance ? entries.get(contextInstance) : undefined);
114
+ if (!entry) {
115
+ throw new Error("useLocker requires a storeKey or a Provider store context.");
116
+ }
117
+ React.useEffect(() => {
118
+ lock(entry);
119
+ return () => unlock(entry);
120
+ }, [entry]);
121
+ return entry.instance;
122
+ },
123
+ getInstance: (storeKey) => {
124
+ if (storeKey === undefined) {
125
+ return undefined;
126
+ }
127
+ return registry.get(storeKey)?.instance;
128
+ },
129
+ };
130
+ return providerStore;
131
+ }
132
+ export function useLocker(store, storeKey) {
133
+ return store.useLocker(storeKey);
134
+ }
@@ -0,0 +1,3 @@
1
+ import type { ProviderStoreEffect } from "./types.js";
2
+ export declare function stateEffect<TState extends object>(deps: Partial<TState>): ProviderStoreEffect<TState>;
3
+ //# sourceMappingURL=effects.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"effects.d.ts","sourceRoot":"","sources":["../src/lib/effects.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AAEtD,wBAAgB,WAAW,CAAC,MAAM,SAAS,MAAM,EAC/C,IAAI,EAAE,OAAO,CAAC,MAAM,CAAC,GACpB,mBAAmB,CAAC,MAAM,CAAC,CAe7B"}
@@ -0,0 +1,14 @@
1
+ import { ZUSTAND } from "./constants.js";
2
+ export function stateEffect(deps) {
3
+ const flatDeps = Object.entries(deps).flat();
4
+ return [
5
+ flatDeps,
6
+ (store, values) => {
7
+ const state = {};
8
+ for (let index = 0; index < values.length; index += 2) {
9
+ state[values[index]] = values[index + 1];
10
+ }
11
+ store[ZUSTAND].setState(state);
12
+ },
13
+ ];
14
+ }
@@ -0,0 +1,8 @@
1
+ export { ZUSTAND } from "./constants.js";
2
+ export { createStore, useLocker } from "./create-store.js";
3
+ export { useStore } from "./use-store.js";
4
+ export { stateEffect } from "./effects.js";
5
+ export { mixin } from "./mixin.js";
6
+ export { composeStore } from "./compose-store.js";
7
+ export type { ActionArgs, ActionReturn, AnyStore, BatchAction, BatchDispatch, BatchDispatchContext, BoundActions, CreateStoreOptions, EqualityFn, GlobalStore, LocalStoreOptions, ProviderProps, ProviderStore, ProviderStoreEffect, SelectorResults, SetState, StoreActionContext, StoreActionDefinitions, StoreDefinition, StoreDefinitionFactory, StoreDispatch, StoreKey, StoreKind, StoreLifecycle, StoreMeta, StoreSelectorDefinitions, StoreInstance, } from "./types.js";
8
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/lib/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,gBAAgB,CAAC;AACzC,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,MAAM,mBAAmB,CAAC;AAC3D,OAAO,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAC;AAC1C,OAAO,EAAE,WAAW,EAAE,MAAM,cAAc,CAAC;AAC3C,OAAO,EAAE,KAAK,EAAE,MAAM,YAAY,CAAC;AACnC,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAElD,YAAY,EACV,UAAU,EACV,YAAY,EACZ,QAAQ,EACR,WAAW,EACX,aAAa,EACb,oBAAoB,EACpB,YAAY,EACZ,kBAAkB,EAClB,UAAU,EACV,WAAW,EACX,iBAAiB,EACjB,aAAa,EACb,aAAa,EACb,mBAAmB,EACnB,eAAe,EACf,QAAQ,EACR,kBAAkB,EAClB,sBAAsB,EACtB,eAAe,EACf,sBAAsB,EACtB,aAAa,EACb,QAAQ,EACR,SAAS,EACT,cAAc,EACd,SAAS,EACT,wBAAwB,EACxB,aAAa,GACd,MAAM,YAAY,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,6 @@
1
+ export { ZUSTAND } from "./constants.js";
2
+ export { createStore, useLocker } from "./create-store.js";
3
+ export { useStore } from "./use-store.js";
4
+ export { stateEffect } from "./effects.js";
5
+ export { mixin } from "./mixin.js";
6
+ export { composeStore } from "./compose-store.js";
@@ -0,0 +1,3 @@
1
+ import type { MixinActions, MixinMeta, MixinSelectors, MixinState, StoreDefinitionFactory } from "./types.js";
2
+ export declare function mixin<const TFactories extends readonly StoreDefinitionFactory<any, any, any, any>[]>(...factories: TFactories): StoreDefinitionFactory<MixinState<TFactories>, MixinActions<TFactories>, MixinSelectors<TFactories, MixinState<TFactories>>, MixinMeta<TFactories>>;
3
+ //# sourceMappingURL=mixin.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mixin.d.ts","sourceRoot":"","sources":["../src/lib/mixin.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,YAAY,EACZ,SAAS,EACT,cAAc,EACd,UAAU,EAEV,sBAAsB,EACvB,MAAM,YAAY,CAAC;AAoBpB,wBAAgB,KAAK,CACnB,KAAK,CAAC,UAAU,SAAS,SAAS,sBAAsB,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,EAAE,EAE9E,GAAG,SAAS,EAAE,UAAU,GACvB,sBAAsB,CACvB,UAAU,CAAC,UAAU,CAAC,EACtB,YAAY,CAAC,UAAU,CAAC,EACxB,cAAc,CAAC,UAAU,EAAE,UAAU,CAAC,UAAU,CAAC,CAAC,EAClD,SAAS,CAAC,UAAU,CAAC,CACtB,CAwDA"}
package/dist/mixin.js ADDED
@@ -0,0 +1,55 @@
1
+ const mergeWithDuplicateCheck = (target, source, label) => {
2
+ if (!source) {
3
+ return;
4
+ }
5
+ for (const [key, value] of Object.entries(source)) {
6
+ if (Object.prototype.hasOwnProperty.call(target, key)) {
7
+ throw new Error(`Duplicate ${label} key "${key}" in mixin().`);
8
+ }
9
+ target[key] = value;
10
+ }
11
+ };
12
+ export function mixin(...factories) {
13
+ return (() => {
14
+ const definitions = factories.map((factory) => factory());
15
+ const state = {};
16
+ const actions = {};
17
+ const selectors = {};
18
+ const meta = {};
19
+ for (const definition of definitions) {
20
+ mergeWithDuplicateCheck(state, definition.state, "state");
21
+ mergeWithDuplicateCheck(actions, definition.actions, "action");
22
+ mergeWithDuplicateCheck(selectors, definition.selectors, "selector");
23
+ Object.assign(meta, definition.meta);
24
+ }
25
+ const hooks = {
26
+ created: (store) => {
27
+ for (const definition of definitions) {
28
+ definition.hooks?.created?.(store);
29
+ }
30
+ },
31
+ mount: (store) => {
32
+ for (const definition of definitions) {
33
+ definition.hooks?.mount?.(store);
34
+ }
35
+ },
36
+ unmount: (store) => {
37
+ for (const definition of definitions) {
38
+ definition.hooks?.unmount?.(store);
39
+ }
40
+ },
41
+ destroy: (store) => {
42
+ for (const definition of definitions) {
43
+ definition.hooks?.destroy?.(store);
44
+ }
45
+ },
46
+ };
47
+ return {
48
+ state,
49
+ actions,
50
+ selectors,
51
+ meta,
52
+ hooks,
53
+ };
54
+ });
55
+ }
@@ -0,0 +1,9 @@
1
+ import type { CreateStoreOptions, LocalStoreOptions, StoreActionDefinitions, StoreDefinitionFactory, StoreInstance, StoreMeta, StoreSelectorDefinitions } from "./types.js";
2
+ export interface RuntimeStore<TState extends object, TActions extends StoreActionDefinitions, TSelectors extends StoreSelectorDefinitions<TState>, TMeta extends StoreMeta> extends StoreInstance<TState, TActions, TSelectors, TMeta> {
3
+ __mount: () => void;
4
+ __unmount: () => void;
5
+ __isDestroyed: () => boolean;
6
+ }
7
+ export type RuntimeOptions = Pick<CreateStoreOptions | LocalStoreOptions, "batch" | "devtools" | "strict">;
8
+ export declare function createRuntimeStore<TState extends object, TActions extends StoreActionDefinitions = {}, TSelectors extends StoreSelectorDefinitions<TState> = {}, TMeta extends StoreMeta = {}>(definitionFactory: StoreDefinitionFactory<TState, TActions, TSelectors, TMeta>, options?: RuntimeOptions): RuntimeStore<TState, TActions, TSelectors, TMeta>;
9
+ //# sourceMappingURL=runtime.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"runtime.d.ts","sourceRoot":"","sources":["../src/lib/runtime.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAGV,kBAAkB,EAElB,iBAAiB,EAIjB,sBAAsB,EACtB,sBAAsB,EACtB,aAAa,EACb,SAAS,EACT,wBAAwB,EACzB,MAAM,YAAY,CAAC;AAKpB,MAAM,WAAW,YAAY,CAC3B,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,EACvC,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,EACnD,KAAK,SAAS,SAAS,CACvB,SAAQ,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC;IAC1D,OAAO,EAAE,MAAM,IAAI,CAAC;IACpB,SAAS,EAAE,MAAM,IAAI,CAAC;IACtB,aAAa,EAAE,MAAM,OAAO,CAAC;CAC9B;AAED,MAAM,MAAM,cAAc,GAAG,IAAI,CAC/B,kBAAkB,GAAG,iBAAiB,EACtC,OAAO,GAAG,UAAU,GAAG,QAAQ,CAChC,CAAC;AAEF,wBAAgB,kBAAkB,CAChC,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,GAAG,EAAE,EAC5C,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GAAG,EAAE,EACxD,KAAK,SAAS,SAAS,GAAG,EAAE,EAE5B,iBAAiB,EAAE,sBAAsB,CACvC,MAAM,EACN,QAAQ,EACR,UAAU,EACV,KAAK,CACN,EACD,OAAO,GAAE,cAAmB,GAC3B,YAAY,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,CAgUnD"}
@@ -0,0 +1,238 @@
1
+ import * as React from "react";
2
+ import { memoize } from "proxy-memoize";
3
+ import { createStore as createZustandStore } from "zustand/vanilla";
4
+ import { devtools } from "zustand/middleware";
5
+ import { ZUSTAND } from "./constants.js";
6
+ const identity = (value) => value;
7
+ const objectIs = Object.is;
8
+ export function createRuntimeStore(definitionFactory, options = {}) {
9
+ const definition = definitionFactory();
10
+ const initialState = definition.state;
11
+ const meta = (definition.meta ?? {});
12
+ const actionDefinitions = (definition.actions ?? {});
13
+ const selectorDefinitions = (definition.selectors ?? {});
14
+ const selectorEntries = Object.entries(selectorDefinitions).map(([key, selector]) => [key, memoize(selector)]);
15
+ const devtoolsName = typeof options.devtools === "object"
16
+ ? options.devtools.name
17
+ : typeof meta.name === "string"
18
+ ? meta.name
19
+ : "simple-nobody-state";
20
+ const creator = () => initialState;
21
+ const zustand = createZustandStore()(options.devtools
22
+ ? devtools(creator, { name: devtoolsName })
23
+ : creator);
24
+ let destroyed = false;
25
+ let mounted = false;
26
+ let batchDepth = 0;
27
+ let queuedState;
28
+ let queuedReplace = false;
29
+ let flushScheduled = false;
30
+ const freezeIfNeeded = (value) => {
31
+ if (options.strict &&
32
+ value !== null &&
33
+ typeof value === "object" &&
34
+ !Object.isFrozen(value)) {
35
+ return Object.freeze(value);
36
+ }
37
+ return value;
38
+ };
39
+ const getWorkingState = () => {
40
+ if (queuedState === undefined) {
41
+ return zustand.getState();
42
+ }
43
+ if (queuedReplace) {
44
+ return queuedState;
45
+ }
46
+ return {
47
+ ...zustand.getState(),
48
+ ...queuedState,
49
+ };
50
+ };
51
+ const flush = () => {
52
+ flushScheduled = false;
53
+ if (queuedState === undefined || destroyed) {
54
+ return;
55
+ }
56
+ const state = queuedState;
57
+ const replace = queuedReplace;
58
+ queuedState = undefined;
59
+ queuedReplace = false;
60
+ zustand.setState(state, replace);
61
+ };
62
+ const scheduleFlush = () => {
63
+ if (flushScheduled || batchDepth > 0) {
64
+ return;
65
+ }
66
+ flushScheduled = true;
67
+ queueMicrotask(flush);
68
+ };
69
+ const setState = (partial, replace = false) => {
70
+ const nextPartial = typeof partial === "function" ? partial(getWorkingState()) : partial;
71
+ if (batchDepth > 0 || options.batch) {
72
+ if (replace || queuedReplace) {
73
+ queuedState = replace
74
+ ? nextPartial
75
+ : {
76
+ ...queuedState,
77
+ ...nextPartial,
78
+ };
79
+ queuedReplace = replace || queuedReplace;
80
+ }
81
+ else {
82
+ queuedState = {
83
+ ...(queuedState ?? {}),
84
+ ...nextPartial,
85
+ };
86
+ }
87
+ if (options.batch && batchDepth === 0) {
88
+ scheduleFlush();
89
+ }
90
+ return;
91
+ }
92
+ zustand.setState(nextPartial, replace);
93
+ };
94
+ const getSelectors = () => {
95
+ const state = getWorkingState();
96
+ const result = {};
97
+ for (const [key, selector] of selectorEntries) {
98
+ result[key] = selector(state);
99
+ }
100
+ return result;
101
+ };
102
+ let store;
103
+ const context = {
104
+ getState: getWorkingState,
105
+ setState,
106
+ get dispatch() {
107
+ return store.dispatch;
108
+ },
109
+ get actions() {
110
+ return actions;
111
+ },
112
+ get selectors() {
113
+ return getSelectors();
114
+ },
115
+ meta,
116
+ };
117
+ const dispatch = ((name, ...args) => {
118
+ const action = actionDefinitions[name];
119
+ if (!action) {
120
+ throw new Error(`Unknown action "${name}".`);
121
+ }
122
+ return action(context, ...args);
123
+ });
124
+ const actions = {};
125
+ for (const key of Object.keys(actionDefinitions)) {
126
+ actions[key] = (...args) => dispatch(key, ...args);
127
+ }
128
+ const useStoreState = (selector = identity, equality = objectIs) => {
129
+ const snapshotRef = React.useRef({
130
+ hasValue: false,
131
+ value: undefined,
132
+ });
133
+ const getSnapshot = React.useCallback(() => {
134
+ const selected = freezeIfNeeded(selector(zustand.getState()));
135
+ const previous = snapshotRef.current;
136
+ if (previous.hasValue && equality(previous.value, selected)) {
137
+ return previous.value;
138
+ }
139
+ snapshotRef.current = { hasValue: true, value: selected };
140
+ return selected;
141
+ }, [equality, selector]);
142
+ return React.useSyncExternalStore(zustand.subscribe, getSnapshot, getSnapshot);
143
+ };
144
+ const useStateRef = (selector = identity) => {
145
+ const ref = React.useRef(freezeIfNeeded(selector(zustand.getState())));
146
+ ref.current = freezeIfNeeded(selector(zustand.getState()));
147
+ React.useEffect(() => zustand.subscribe((nextState) => {
148
+ ref.current = freezeIfNeeded(selector(nextState));
149
+ }), [selector]);
150
+ return ref;
151
+ };
152
+ const finishBatch = () => {
153
+ batchDepth = Math.max(0, batchDepth - 1);
154
+ if (batchDepth === 0) {
155
+ flush();
156
+ }
157
+ };
158
+ const batchDispatch = ((fnOrActions) => {
159
+ batchDepth += 1;
160
+ try {
161
+ const result = Array.isArray(fnOrActions)
162
+ ? fnOrActions.forEach(([name, ...args]) => {
163
+ dispatch(name, ...args);
164
+ })
165
+ : fnOrActions({
166
+ getState: getWorkingState,
167
+ dispatch,
168
+ actions,
169
+ get selectors() {
170
+ return getSelectors();
171
+ },
172
+ meta,
173
+ });
174
+ if (result && typeof result.then === "function") {
175
+ return result.then((value) => {
176
+ finishBatch();
177
+ return value;
178
+ }, (error) => {
179
+ finishBatch();
180
+ throw error;
181
+ });
182
+ }
183
+ finishBatch();
184
+ return result;
185
+ }
186
+ catch (error) {
187
+ finishBatch();
188
+ throw error;
189
+ }
190
+ });
191
+ store = {
192
+ [ZUSTAND]: zustand,
193
+ useState: useStoreState,
194
+ useStateRef: useStateRef,
195
+ useActions: () => actions,
196
+ get actions() {
197
+ return actions;
198
+ },
199
+ get state() {
200
+ return getWorkingState();
201
+ },
202
+ get selectors() {
203
+ return getSelectors();
204
+ },
205
+ get meta() {
206
+ return meta;
207
+ },
208
+ getState: getWorkingState,
209
+ dispatch,
210
+ batchDispatch,
211
+ subscribe: zustand.subscribe,
212
+ destroy: () => {
213
+ if (destroyed) {
214
+ return;
215
+ }
216
+ flush();
217
+ destroyed = true;
218
+ definition.hooks?.destroy?.(store);
219
+ },
220
+ __mount: () => {
221
+ if (destroyed || mounted) {
222
+ return;
223
+ }
224
+ mounted = true;
225
+ definition.hooks?.mount?.(store);
226
+ },
227
+ __unmount: () => {
228
+ if (destroyed || !mounted) {
229
+ return;
230
+ }
231
+ mounted = false;
232
+ definition.hooks?.unmount?.(store);
233
+ },
234
+ __isDestroyed: () => destroyed,
235
+ };
236
+ definition.hooks?.created?.(store);
237
+ return store;
238
+ }
@@ -0,0 +1,118 @@
1
+ import type * as React from "react";
2
+ import type { StoreApi } from "zustand/vanilla";
3
+ import type { STORE_KIND, ZUSTAND } from "./constants.js";
4
+ export type StoreKey = string | number | symbol;
5
+ export type StoreMeta = {
6
+ [key: string]: any;
7
+ };
8
+ export type EqualityFn<T> = (a: T, b: T) => boolean;
9
+ export type StoreKind = "globalStore" | "providerStore";
10
+ export type SetState<TState extends object> = (partial: Partial<TState> | TState | ((state: TState) => Partial<TState> | TState), replace?: boolean) => void;
11
+ export type ActionArgs<TAction> = TAction extends (ctx: any, ...args: infer TArgs) => any ? TArgs : never;
12
+ export type ActionReturn<TAction> = TAction extends (ctx: any, ...args: any[]) => infer TReturn ? TReturn : never;
13
+ export type StoreActionDefinitions = Record<string, (ctx: any, ...args: any[]) => any>;
14
+ export type StoreSelectorDefinitions<TState extends object> = Record<string, (state: TState) => any>;
15
+ export type BoundActions<TActions extends StoreActionDefinitions> = {
16
+ readonly [K in keyof TActions]: (...args: ActionArgs<TActions[K]>) => ActionReturn<TActions[K]>;
17
+ };
18
+ export type StoreDispatch<TActions extends StoreActionDefinitions> = <K extends Extract<keyof TActions, string>>(name: K, ...args: ActionArgs<TActions[K]>) => ActionReturn<TActions[K]>;
19
+ export type SelectorResults<TSelectors extends StoreSelectorDefinitions<TState>, TState extends object> = {
20
+ readonly [K in keyof TSelectors]: ReturnType<TSelectors[K]>;
21
+ };
22
+ export interface StoreActionContext<TState extends object, TActions extends StoreActionDefinitions, TSelectors extends StoreSelectorDefinitions<TState>, TMeta extends StoreMeta> {
23
+ getState: () => TState;
24
+ setState: SetState<TState>;
25
+ dispatch: StoreDispatch<TActions>;
26
+ actions: BoundActions<TActions>;
27
+ selectors: SelectorResults<TSelectors, TState>;
28
+ meta: TMeta;
29
+ }
30
+ export interface StoreLifecycle<TState extends object, TActions extends StoreActionDefinitions, TSelectors extends StoreSelectorDefinitions<TState>, TMeta extends StoreMeta> {
31
+ created?: (store: StoreInstance<TState, TActions, TSelectors, TMeta>) => void;
32
+ mount?: (store: StoreInstance<TState, TActions, TSelectors, TMeta>) => void;
33
+ unmount?: (store: StoreInstance<TState, TActions, TSelectors, TMeta>) => void;
34
+ destroy?: (store: StoreInstance<TState, TActions, TSelectors, TMeta>) => void;
35
+ }
36
+ export interface StoreDefinition<TState extends object, TActions extends StoreActionDefinitions = {}, TSelectors extends StoreSelectorDefinitions<TState> = {}, TMeta extends StoreMeta = {}> {
37
+ state: TState;
38
+ actions?: TActions;
39
+ selectors?: TSelectors;
40
+ meta?: TMeta;
41
+ hooks?: StoreLifecycle<TState, TActions, TSelectors, TMeta>;
42
+ }
43
+ export type StoreDefinitionFactory<TState extends object, TActions extends StoreActionDefinitions = {}, TSelectors extends StoreSelectorDefinitions<TState> = {}, TMeta extends StoreMeta = {}> = () => StoreDefinition<TState, TActions, TSelectors, TMeta>;
44
+ export interface CreateStoreOptions<TKind extends StoreKind = StoreKind> {
45
+ strict?: boolean;
46
+ batch?: boolean;
47
+ devtools?: boolean | {
48
+ name?: string;
49
+ };
50
+ storeType: TKind;
51
+ }
52
+ export type LocalStoreOptions = Omit<CreateStoreOptions, "storeType">;
53
+ export type BatchAction<TActions extends StoreActionDefinitions> = {
54
+ [K in Extract<keyof TActions, string>]: [
55
+ name: K,
56
+ ...args: ActionArgs<TActions[K]>
57
+ ];
58
+ }[Extract<keyof TActions, string>];
59
+ export interface BatchDispatchContext<TState extends object, TActions extends StoreActionDefinitions, TSelectors extends StoreSelectorDefinitions<TState>, TMeta extends StoreMeta> {
60
+ getState: () => TState;
61
+ dispatch: StoreDispatch<TActions>;
62
+ actions: BoundActions<TActions>;
63
+ selectors: SelectorResults<TSelectors, TState>;
64
+ meta: TMeta;
65
+ }
66
+ export type BatchDispatch<TState extends object, TActions extends StoreActionDefinitions, TSelectors extends StoreSelectorDefinitions<TState>, TMeta extends StoreMeta> = {
67
+ <TReturn>(fn: (ctx: BatchDispatchContext<TState, TActions, TSelectors, TMeta>) => TReturn): TReturn;
68
+ (actions: Array<BatchAction<TActions>>): void;
69
+ };
70
+ export interface StoreInstance<TState extends object, TActions extends StoreActionDefinitions = {}, TSelectors extends StoreSelectorDefinitions<TState> = {}, TMeta extends StoreMeta = {}> {
71
+ useState(): TState;
72
+ useState<TSelected>(selector: (state: TState) => TSelected, equality?: EqualityFn<TSelected>): TSelected;
73
+ useStateRef(): React.MutableRefObject<TState>;
74
+ useStateRef<TSelected>(selector: (state: TState) => TSelected): React.MutableRefObject<TSelected>;
75
+ useActions: () => BoundActions<TActions>;
76
+ readonly actions: BoundActions<TActions>;
77
+ readonly state: TState;
78
+ readonly selectors: SelectorResults<TSelectors, TState>;
79
+ readonly meta: TMeta;
80
+ getState: () => TState;
81
+ dispatch: StoreDispatch<TActions>;
82
+ batchDispatch: BatchDispatch<TState, TActions, TSelectors, TMeta>;
83
+ subscribe: StoreApi<TState>["subscribe"];
84
+ destroy: () => void;
85
+ readonly [ZUSTAND]: StoreApi<TState>;
86
+ }
87
+ export type ProviderStoreEffect<TState extends object> = [
88
+ deps: unknown[],
89
+ effect: (store: StoreInstance<TState, any, any, any>, deps: unknown[]) => void
90
+ ];
91
+ export interface ProviderProps<TState extends object> {
92
+ children?: React.ReactNode;
93
+ storeKey?: StoreKey;
94
+ effect?: ProviderStoreEffect<TState>;
95
+ }
96
+ export interface GlobalStore<TState extends object, TActions extends StoreActionDefinitions = {}, TSelectors extends StoreSelectorDefinitions<TState> = {}, TMeta extends StoreMeta = {}> extends StoreInstance<TState, TActions, TSelectors, TMeta> {
97
+ readonly [STORE_KIND]: "globalStore";
98
+ }
99
+ export interface ProviderStore<TState extends object, TActions extends StoreActionDefinitions = {}, TSelectors extends StoreSelectorDefinitions<TState> = {}, TMeta extends StoreMeta = {}> {
100
+ Provider: React.FC<ProviderProps<TState>>;
101
+ useState(): TState;
102
+ useState<TSelected>(selector: (state: TState) => TSelected, equality?: EqualityFn<TSelected>): TSelected;
103
+ useStateRef(): React.MutableRefObject<TState>;
104
+ useStateRef<TSelected>(selector: (state: TState) => TSelected): React.MutableRefObject<TSelected>;
105
+ useActions: () => BoundActions<TActions>;
106
+ useInstance: () => StoreInstance<TState, TActions, TSelectors, TMeta>;
107
+ useLocker: (storeKey?: StoreKey) => StoreInstance<TState, TActions, TSelectors, TMeta>;
108
+ getInstance: (storeKey?: StoreKey) => StoreInstance<TState, TActions, TSelectors, TMeta> | undefined;
109
+ readonly [STORE_KIND]: "providerStore";
110
+ }
111
+ export type AnyStore = GlobalStore<any, any, any, any> | ProviderStore<any, any, any, any>;
112
+ type UnionToIntersection<TUnion> = (TUnion extends any ? (value: TUnion) => void : never) extends (value: infer TIntersection) => void ? TIntersection : never;
113
+ export type MixinState<TFactories extends readonly StoreDefinitionFactory<any, any, any, any>[]> = UnionToIntersection<ReturnType<TFactories[number]> extends StoreDefinition<infer TState, any, any, any> ? TState : never> extends infer TState ? TState extends object ? TState : object : object;
114
+ export type MixinActions<TFactories extends readonly StoreDefinitionFactory<any, any, any, any>[]> = UnionToIntersection<ReturnType<TFactories[number]> extends StoreDefinition<any, infer TActions, any, any> ? TActions : never> extends infer TActions ? TActions extends StoreActionDefinitions ? TActions : {} : {};
115
+ export type MixinSelectors<TFactories extends readonly StoreDefinitionFactory<any, any, any, any>[], TState extends object> = UnionToIntersection<ReturnType<TFactories[number]> extends StoreDefinition<any, any, infer TSelectors, any> ? TSelectors : never> extends infer TSelectors ? TSelectors extends StoreSelectorDefinitions<TState> ? TSelectors : {} : {};
116
+ export type MixinMeta<TFactories extends readonly StoreDefinitionFactory<any, any, any, any>[]> = UnionToIntersection<ReturnType<TFactories[number]> extends StoreDefinition<any, any, any, infer TMeta> ? TMeta : never> extends infer TMeta ? TMeta extends StoreMeta ? TMeta : {} : {};
117
+ export {};
118
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/lib/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,KAAK,MAAM,OAAO,CAAC;AACpC,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AAChD,OAAO,KAAK,EAAE,UAAU,EAAE,OAAO,EAAE,MAAM,gBAAgB,CAAC;AAE1D,MAAM,MAAM,QAAQ,GAAG,MAAM,GAAG,MAAM,GAAG,MAAM,CAAC;AAChD,MAAM,MAAM,SAAS,GAAG;IAAE,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,CAAA;CAAE,CAAC;AAC/C,MAAM,MAAM,UAAU,CAAC,CAAC,IAAI,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,CAAC,KAAK,OAAO,CAAC;AAEpD,MAAM,MAAM,SAAS,GAAG,aAAa,GAAG,eAAe,CAAC;AAExD,MAAM,MAAM,QAAQ,CAAC,MAAM,SAAS,MAAM,IAAI,CAC5C,OAAO,EACH,OAAO,CAAC,MAAM,CAAC,GACf,MAAM,GACN,CAAC,CAAC,KAAK,EAAE,MAAM,KAAK,OAAO,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,EACjD,OAAO,CAAC,EAAE,OAAO,KACd,IAAI,CAAC;AAEV,MAAM,MAAM,UAAU,CAAC,OAAO,IAAI,OAAO,SAAS,CAChD,GAAG,EAAE,GAAG,EACR,GAAG,IAAI,EAAE,MAAM,KAAK,KACjB,GAAG,GACJ,KAAK,GACL,KAAK,CAAC;AAEV,MAAM,MAAM,YAAY,CAAC,OAAO,IAAI,OAAO,SAAS,CAClD,GAAG,EAAE,GAAG,EACR,GAAG,IAAI,EAAE,GAAG,EAAE,KACX,MAAM,OAAO,GACd,OAAO,GACP,KAAK,CAAC;AAEV,MAAM,MAAM,sBAAsB,GAAG,MAAM,CACzC,MAAM,EACN,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,IAAI,EAAE,GAAG,EAAE,KAAK,GAAG,CAClC,CAAC;AAEF,MAAM,MAAM,wBAAwB,CAAC,MAAM,SAAS,MAAM,IAAI,MAAM,CAClE,MAAM,EACN,CAAC,KAAK,EAAE,MAAM,KAAK,GAAG,CACvB,CAAC;AAEF,MAAM,MAAM,YAAY,CAAC,QAAQ,SAAS,sBAAsB,IAAI;IAClE,QAAQ,EAAE,CAAC,IAAI,MAAM,QAAQ,GAAG,CAC9B,GAAG,IAAI,EAAE,UAAU,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,KAC7B,YAAY,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC;CAC/B,CAAC;AAEF,MAAM,MAAM,aAAa,CAAC,QAAQ,SAAS,sBAAsB,IAAI,CACnE,CAAC,SAAS,OAAO,CAAC,MAAM,QAAQ,EAAE,MAAM,CAAC,EAEzC,IAAI,EAAE,CAAC,EACP,GAAG,IAAI,EAAE,UAAU,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,KAC7B,YAAY,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC;AAE/B,MAAM,MAAM,eAAe,CACzB,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,EACnD,MAAM,SAAS,MAAM,IACnB;IACF,QAAQ,EAAE,CAAC,IAAI,MAAM,UAAU,GAAG,UAAU,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC;CAC5D,CAAC;AAEF,MAAM,WAAW,kBAAkB,CACjC,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,EACvC,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,EACnD,KAAK,SAAS,SAAS;IAEvB,QAAQ,EAAE,MAAM,MAAM,CAAC;IACvB,QAAQ,EAAE,QAAQ,CAAC,MAAM,CAAC,CAAC;IAC3B,QAAQ,EAAE,aAAa,CAAC,QAAQ,CAAC,CAAC;IAClC,OAAO,EAAE,YAAY,CAAC,QAAQ,CAAC,CAAC;IAChC,SAAS,EAAE,eAAe,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;IAC/C,IAAI,EAAE,KAAK,CAAC;CACb;AAED,MAAM,WAAW,cAAc,CAC7B,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,EACvC,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,EACnD,KAAK,SAAS,SAAS;IAEvB,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,KAAK,IAAI,CAAC;IAC9E,KAAK,CAAC,EAAE,CAAC,KAAK,EAAE,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,KAAK,IAAI,CAAC;IAC5E,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,KAAK,IAAI,CAAC;IAC9E,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,KAAK,IAAI,CAAC;CAC/E;AAED,MAAM,WAAW,eAAe,CAC9B,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,GAAG,EAAE,EAC5C,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GAAG,EAAE,EACxD,KAAK,SAAS,SAAS,GAAG,EAAE;IAE5B,KAAK,EAAE,MAAM,CAAC;IACd,OAAO,CAAC,EAAE,QAAQ,CAAC;IACnB,SAAS,CAAC,EAAE,UAAU,CAAC;IACvB,IAAI,CAAC,EAAE,KAAK,CAAC;IACb,KAAK,CAAC,EAAE,cAAc,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,CAAC;CAC7D;AAED,MAAM,MAAM,sBAAsB,CAChC,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,GAAG,EAAE,EAC5C,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GAAG,EAAE,EACxD,KAAK,SAAS,SAAS,GAAG,EAAE,IAC1B,MAAM,eAAe,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,CAAC;AAE/D,MAAM,WAAW,kBAAkB,CAAC,KAAK,SAAS,SAAS,GAAG,SAAS;IACrE,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,QAAQ,CAAC,EAAE,OAAO,GAAG;QAAE,IAAI,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;IACvC,SAAS,EAAE,KAAK,CAAC;CAClB;AAED,MAAM,MAAM,iBAAiB,GAAG,IAAI,CAAC,kBAAkB,EAAE,WAAW,CAAC,CAAC;AAEtE,MAAM,MAAM,WAAW,CAAC,QAAQ,SAAS,sBAAsB,IAAI;KAChE,CAAC,IAAI,OAAO,CAAC,MAAM,QAAQ,EAAE,MAAM,CAAC,GAAG;QACtC,IAAI,EAAE,CAAC;QACP,GAAG,IAAI,EAAE,UAAU,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC;KACjC;CACF,CAAC,OAAO,CAAC,MAAM,QAAQ,EAAE,MAAM,CAAC,CAAC,CAAC;AAEnC,MAAM,WAAW,oBAAoB,CACnC,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,EACvC,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,EACnD,KAAK,SAAS,SAAS;IAEvB,QAAQ,EAAE,MAAM,MAAM,CAAC;IACvB,QAAQ,EAAE,aAAa,CAAC,QAAQ,CAAC,CAAC;IAClC,OAAO,EAAE,YAAY,CAAC,QAAQ,CAAC,CAAC;IAChC,SAAS,EAAE,eAAe,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;IAC/C,IAAI,EAAE,KAAK,CAAC;CACb;AAED,MAAM,MAAM,aAAa,CACvB,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,EACvC,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,EACnD,KAAK,SAAS,SAAS,IACrB;IACF,CAAC,OAAO,EACN,EAAE,EAAE,CACF,GAAG,EAAE,oBAAoB,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,KAC3D,OAAO,GACX,OAAO,CAAC;IACX,CAAC,OAAO,EAAE,KAAK,CAAC,WAAW,CAAC,QAAQ,CAAC,CAAC,GAAG,IAAI,CAAC;CAC/C,CAAC;AAEF,MAAM,WAAW,aAAa,CAC5B,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,GAAG,EAAE,EAC5C,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GAAG,EAAE,EACxD,KAAK,SAAS,SAAS,GAAG,EAAE;IAE5B,QAAQ,IAAI,MAAM,CAAC;IACnB,QAAQ,CAAC,SAAS,EAChB,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,SAAS,EACtC,QAAQ,CAAC,EAAE,UAAU,CAAC,SAAS,CAAC,GAC/B,SAAS,CAAC;IACb,WAAW,IAAI,KAAK,CAAC,gBAAgB,CAAC,MAAM,CAAC,CAAC;IAC9C,WAAW,CAAC,SAAS,EACnB,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,SAAS,GACrC,KAAK,CAAC,gBAAgB,CAAC,SAAS,CAAC,CAAC;IACrC,UAAU,EAAE,MAAM,YAAY,CAAC,QAAQ,CAAC,CAAC;IACzC,QAAQ,CAAC,OAAO,EAAE,YAAY,CAAC,QAAQ,CAAC,CAAC;IACzC,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,SAAS,EAAE,eAAe,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC;IACxD,QAAQ,CAAC,IAAI,EAAE,KAAK,CAAC;IACrB,QAAQ,EAAE,MAAM,MAAM,CAAC;IACvB,QAAQ,EAAE,aAAa,CAAC,QAAQ,CAAC,CAAC;IAClC,aAAa,EAAE,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,CAAC;IAClE,SAAS,EAAE,QAAQ,CAAC,MAAM,CAAC,CAAC,WAAW,CAAC,CAAC;IACzC,OAAO,EAAE,MAAM,IAAI,CAAC;IACpB,QAAQ,CAAC,CAAC,OAAO,CAAC,EAAE,QAAQ,CAAC,MAAM,CAAC,CAAC;CACtC;AAED,MAAM,MAAM,mBAAmB,CAAC,MAAM,SAAS,MAAM,IAAI;IACvD,IAAI,EAAE,OAAO,EAAE;IACf,MAAM,EAAE,CAAC,KAAK,EAAE,aAAa,CAAC,MAAM,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,IAAI;CAC/E,CAAC;AAEF,MAAM,WAAW,aAAa,CAAC,MAAM,SAAS,MAAM;IAClD,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAC;IAC3B,QAAQ,CAAC,EAAE,QAAQ,CAAC;IACpB,MAAM,CAAC,EAAE,mBAAmB,CAAC,MAAM,CAAC,CAAC;CACtC;AAED,MAAM,WAAW,WAAW,CAC1B,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,GAAG,EAAE,EAC5C,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GAAG,EAAE,EACxD,KAAK,SAAS,SAAS,GAAG,EAAE,CAC5B,SAAQ,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC;IAC1D,QAAQ,CAAC,CAAC,UAAU,CAAC,EAAE,aAAa,CAAC;CACtC;AAED,MAAM,WAAW,aAAa,CAC5B,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,GAAG,EAAE,EAC5C,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GAAG,EAAE,EACxD,KAAK,SAAS,SAAS,GAAG,EAAE;IAE5B,QAAQ,EAAE,KAAK,CAAC,EAAE,CAAC,aAAa,CAAC,MAAM,CAAC,CAAC,CAAC;IAC1C,QAAQ,IAAI,MAAM,CAAC;IACnB,QAAQ,CAAC,SAAS,EAChB,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,SAAS,EACtC,QAAQ,CAAC,EAAE,UAAU,CAAC,SAAS,CAAC,GAC/B,SAAS,CAAC;IACb,WAAW,IAAI,KAAK,CAAC,gBAAgB,CAAC,MAAM,CAAC,CAAC;IAC9C,WAAW,CAAC,SAAS,EACnB,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,SAAS,GACrC,KAAK,CAAC,gBAAgB,CAAC,SAAS,CAAC,CAAC;IACrC,UAAU,EAAE,MAAM,YAAY,CAAC,QAAQ,CAAC,CAAC;IACzC,WAAW,EAAE,MAAM,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,CAAC;IACtE,SAAS,EAAE,CAAC,QAAQ,CAAC,EAAE,QAAQ,KAAK,aAAa,CAC/C,MAAM,EACN,QAAQ,EACR,UAAU,EACV,KAAK,CACN,CAAC;IACF,WAAW,EAAE,CACX,QAAQ,CAAC,EAAE,QAAQ,KAChB,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,GAAG,SAAS,CAAC;IACpE,QAAQ,CAAC,CAAC,UAAU,CAAC,EAAE,eAAe,CAAC;CACxC;AAED,MAAM,MAAM,QAAQ,GAChB,WAAW,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,GAC/B,aAAa,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC;AAEtC,KAAK,mBAAmB,CAAC,MAAM,IAAI,CACjC,MAAM,SAAS,GAAG,GAAG,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,GAAG,KAAK,CACrD,SAAS,CAAC,KAAK,EAAE,MAAM,aAAa,KAAK,IAAI,GAC1C,aAAa,GACb,KAAK,CAAC;AAEV,MAAM,MAAM,UAAU,CACpB,UAAU,SAAS,SAAS,sBAAsB,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,EAAE,IACtE,mBAAmB,CACrB,UAAU,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC,SAAS,eAAe,CAAC,MAAM,MAAM,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,GAC/E,MAAM,GACN,KAAK,CACV,SAAS,MAAM,MAAM,GAClB,MAAM,SAAS,MAAM,GACnB,MAAM,GACN,MAAM,GACR,MAAM,CAAC;AAEX,MAAM,MAAM,YAAY,CACtB,UAAU,SAAS,SAAS,sBAAsB,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,EAAE,IACtE,mBAAmB,CACrB,UAAU,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC,SAAS,eAAe,CAAC,GAAG,EAAE,MAAM,QAAQ,EAAE,GAAG,EAAE,GAAG,CAAC,GACjF,QAAQ,GACR,KAAK,CACV,SAAS,MAAM,QAAQ,GACpB,QAAQ,SAAS,sBAAsB,GACrC,QAAQ,GACR,EAAE,GACJ,EAAE,CAAC;AAEP,MAAM,MAAM,cAAc,CACxB,UAAU,SAAS,SAAS,sBAAsB,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,EAAE,EACxE,MAAM,SAAS,MAAM,IACnB,mBAAmB,CACrB,UAAU,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC,SAAS,eAAe,CAAC,GAAG,EAAE,GAAG,EAAE,MAAM,UAAU,EAAE,GAAG,CAAC,GACnF,UAAU,GACV,KAAK,CACV,SAAS,MAAM,UAAU,GACtB,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GACjD,UAAU,GACV,EAAE,GACJ,EAAE,CAAC;AAEP,MAAM,MAAM,SAAS,CACnB,UAAU,SAAS,SAAS,sBAAsB,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,EAAE,IACtE,mBAAmB,CACrB,UAAU,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC,SAAS,eAAe,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,MAAM,KAAK,CAAC,GAC9E,KAAK,GACL,KAAK,CACV,SAAS,MAAM,KAAK,GACjB,KAAK,SAAS,SAAS,GACrB,KAAK,GACL,EAAE,GACJ,EAAE,CAAC"}
package/dist/types.js ADDED
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,3 @@
1
+ import type { LocalStoreOptions, StoreActionDefinitions, StoreDefinitionFactory, StoreInstance, StoreMeta, StoreSelectorDefinitions } from "./types.js";
2
+ export declare function useStore<TState extends object, TActions extends StoreActionDefinitions = {}, TSelectors extends StoreSelectorDefinitions<TState> = {}, TMeta extends StoreMeta = {}>(definition: StoreDefinitionFactory<TState, TActions, TSelectors, TMeta>, options?: LocalStoreOptions): StoreInstance<TState, TActions, TSelectors, TMeta>;
3
+ //# sourceMappingURL=use-store.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-store.d.ts","sourceRoot":"","sources":["../src/lib/use-store.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EACV,iBAAiB,EACjB,sBAAsB,EACtB,sBAAsB,EACtB,aAAa,EACb,SAAS,EACT,wBAAwB,EACzB,MAAM,YAAY,CAAC;AAEpB,wBAAgB,QAAQ,CACtB,MAAM,SAAS,MAAM,EACrB,QAAQ,SAAS,sBAAsB,GAAG,EAAE,EAC5C,UAAU,SAAS,wBAAwB,CAAC,MAAM,CAAC,GAAG,EAAE,EACxD,KAAK,SAAS,SAAS,GAAG,EAAE,EAE5B,UAAU,EAAE,sBAAsB,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,EACvE,OAAO,GAAE,iBAAsB,GAC9B,aAAa,CAAC,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,KAAK,CAAC,CAqBpD"}
@@ -0,0 +1,16 @@
1
+ import * as React from "react";
2
+ import { createRuntimeStore } from "./runtime.js";
3
+ export function useStore(definition, options = {}) {
4
+ const storeRef = React.useRef();
5
+ if (!storeRef.current) {
6
+ storeRef.current = createRuntimeStore(definition, options);
7
+ }
8
+ React.useEffect(() => {
9
+ storeRef.current?.__mount?.();
10
+ return () => {
11
+ storeRef.current?.__unmount?.();
12
+ storeRef.current?.destroy();
13
+ };
14
+ }, []);
15
+ return storeRef.current;
16
+ }
package/package.json ADDED
@@ -0,0 +1,56 @@
1
+ {
2
+ "name": "@feiyeyuji/simple-nobody-state",
3
+ "version": "0.1.0",
4
+ "description": "A tiny Zustand-powered state toolkit with DI providers, local stores, memoized selectors, batching, and strong TypeScript inference.",
5
+ "type": "module",
6
+ "sideEffects": false,
7
+ "files": [
8
+ "dist",
9
+ "README.md"
10
+ ],
11
+ "exports": {
12
+ ".": {
13
+ "types": "./dist/index.d.ts",
14
+ "import": "./dist/index.js"
15
+ }
16
+ },
17
+ "scripts": {
18
+ "build": "tsc --build tsconfig.build.json",
19
+ "typecheck": "tsc --noEmit --project tsconfig.json",
20
+ "test": "node --experimental-vm-modules node_modules/jest/bin/jest.js --runInBand",
21
+ "examples": "HOME=.storybook-home STORYBOOK_DISABLE_TELEMETRY=1 storybook dev -p 6006",
22
+ "build:examples": "HOME=.storybook-home STORYBOOK_DISABLE_TELEMETRY=1 storybook build"
23
+ },
24
+ "keywords": [
25
+ "zustand",
26
+ "react",
27
+ "state",
28
+ "typescript",
29
+ "dependency-injection"
30
+ ],
31
+ "peerDependencies": {
32
+ "react": ">=18",
33
+ "react-dom": ">=18"
34
+ },
35
+ "dependencies": {
36
+ "proxy-memoize": "^3.0.1",
37
+ "zustand": "^5.0.0"
38
+ },
39
+ "devDependencies": {
40
+ "@storybook/react-vite": "^8.6.18",
41
+ "@testing-library/dom": "^10.4.0",
42
+ "@testing-library/jest-dom": "^6.6.3",
43
+ "@testing-library/react": "^16.1.0",
44
+ "@types/jest": "^29.5.14",
45
+ "@types/react": "^18.3.12",
46
+ "@types/react-dom": "^18.3.1",
47
+ "jest": "^29.7.0",
48
+ "jest-environment-jsdom": "^29.7.0",
49
+ "react": "^18.3.1",
50
+ "react-dom": "^18.3.1",
51
+ "storybook": "^8.6.18",
52
+ "ts-jest": "^29.2.5",
53
+ "typescript": "^5.6.3",
54
+ "vite": "^6.4.2"
55
+ }
56
+ }