atomaric 0.0.45 → 0.0.60

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/src/test.tsx ADDED
@@ -0,0 +1,207 @@
1
+ import React, { useEffect, useSyncExternalStore } from 'react';
2
+ import { createRoot } from 'react-dom/client';
3
+ import { atom, configureAtomaric, useAtomDo, useAtomValue } from './lib';
4
+
5
+ configureAtomaric({ useSyncExternalStore, keyPathSeparator: '.' });
6
+
7
+ createRoot(document.getElementById('root')!).render(
8
+ <React.StrictMode>
9
+ <App />
10
+ </React.StrictMode>,
11
+ );
12
+
13
+ const testAtom = atom(new Set<number>(), {
14
+ storeKey: 'test:set',
15
+ do: set => ({
16
+ update12: () => set(prev => new Set(prev).add(12)),
17
+ }),
18
+ });
19
+
20
+ const testTextAtom = atom('', {
21
+ storeKey: 'test:text',
22
+ unchangable: true,
23
+ exp: () => new Date(Date.now() + 3 * 1000),
24
+
25
+ zipValue: value => ({ value }),
26
+ unzipValue: val => val.value,
27
+
28
+ do: set => ({
29
+ addText: (text: string) => {
30
+ set(prev => prev + text);
31
+ },
32
+ }),
33
+ });
34
+
35
+ const array: (number | '')[] = [3, 1, 7, 4, 8, 9, 5];
36
+ const arrayAtom = atom(array, {
37
+ do: () => ({
38
+ nothing: () => {},
39
+ }),
40
+ });
41
+
42
+ console.info(Object.keys(arrayAtom));
43
+ // arrayAtom.do.filter = {};
44
+
45
+ console.info(arrayAtom);
46
+ arrayAtom.do.push(0);
47
+ arrayAtom.do.nothing();
48
+ console.info(arrayAtom.get());
49
+ arrayAtom.do.unshift(-1);
50
+ console.info(arrayAtom.get());
51
+ arrayAtom.do.update(arr => arr.sort());
52
+ console.info(arrayAtom.get());
53
+ arrayAtom.do.filter();
54
+ console.info(arrayAtom.get());
55
+
56
+ atom(0, 'a:a');
57
+ atom(0, { storeKey: 'a:a' });
58
+ atom(0, { storeKey: 'a:a', warnOnDuplicateStoreKey: false });
59
+
60
+ (function testDeepPartialChanges() {
61
+ const b = { c: [{ d: 8, e: 'e', f: 'F' }] };
62
+ const a = { f: { g: '' }, b };
63
+ const deepTest = atom({ a, b });
64
+
65
+ deepTest.do.setDeepPartial('b.c.0.d', 123, { b: { c: [{}] } });
66
+ deepTest.do.setDeepPartial('b+c+8+e', 'EE', null, '+');
67
+
68
+ console.info(deepTest.get(), deepTest.get().a.f === a.f, deepTest.get().b.c === b.c);
69
+ })();
70
+
71
+ (function testDeepPartialChanges() {
72
+ const enum Id {
73
+ def = 0,
74
+ }
75
+
76
+ const deepTest = atom(
77
+ {} as Record<
78
+ Id,
79
+ {
80
+ in: { inin: [{ ininin: number }] }[];
81
+ out: { some: { req: 0 } };
82
+ else: { if: {} };
83
+ }
84
+ >,
85
+ );
86
+
87
+ deepTest.do.setDeepPartial(`${Id.def}.in.${9}.inin.0`, { ininin: 9 }, { [Id.def]: { in: [{ inin: [] }] } });
88
+ console.info('Id.def', deepTest.get());
89
+
90
+ deepTest.do.setDeepPartial(`${Id.def}+in+ 4 +inin+0+ininin`, () => 7, { [Id.def]: { in: [{ inin: [{}] }] } }, '+');
91
+ console.info('Id.def', deepTest.get());
92
+
93
+ // will throw
94
+ // console.error(deepTest.get()[Id.def]?.out.some.req);
95
+ })();
96
+
97
+ (function testDeepPartialSetWithDonor() {
98
+ const a: {
99
+ val: {
100
+ b?: { c?: { f: { g?: { e: string } }[] }[] };
101
+ f: { l: number; g?: number };
102
+ };
103
+ } = { val: { f: { l: 9 } } };
104
+
105
+ const deepTest = atom(a);
106
+
107
+ deepTest.do.setDeepPartial('val.b.c.4.f', [{ g: { e: '^' } }], { val: { b: { c: [{}] } } });
108
+ deepTest.do.setDeepPartial('val.b.c.4.f.5.g', { e: '!!@' }, { val: { b: { c: [{ f: [{}] }] } } });
109
+ deepTest.do.setDeepPartial('val.b.c.4.f.2', { g: { e: '2' } }, { val: { b: { c: [{ f: [] }] } } });
110
+ deepTest.do.setDeepPartial('val.b.c.4.f.5.g.e', 'FIVE', { val: { b: { c: [{ f: [{ g: {} }] }] } } });
111
+ deepTest.do.setDeepPartial('val.f.l', 123, { val: { f: {} } });
112
+
113
+ deepTest.do.setDeepPartial('val***f***g', 777, { val: { f: {} } }, '***');
114
+
115
+ console.info(deepTest.get());
116
+ })();
117
+
118
+ (function testUpdate() {
119
+ const a: {
120
+ val: {
121
+ b: { c: { f: { g: { e: string } }[] }[] };
122
+ };
123
+ f: { l: { v: { r: number } }; g?: number };
124
+ num: number;
125
+ } = {
126
+ val: { b: { c: [{ f: [{ g: { e: '1' } }] }] } },
127
+ f: { l: { v: { r: 8 } } },
128
+ num: 8,
129
+ };
130
+
131
+ const updateTest = atom(a);
132
+
133
+ const prevF = a.val.b.c[0].f;
134
+ const prevV = a.f.l.v;
135
+
136
+ console.info(updateTest.get() === a);
137
+
138
+ updateTest.do.update(a => {
139
+ a.val.b.c[0].f[0].g.e = '2';
140
+ // a.num = 0;
141
+ });
142
+ console.info(
143
+ updateTest.get() === a,
144
+ prevF === a.val.b.c[0].f,
145
+ prevV === updateTest.get().f.l.v,
146
+ updateTest.get().val.b.c[0].f === a.val.b.c[0].f,
147
+ a.val.b.c[0].f[0].g,
148
+ updateTest.get().val.b.c[0].f[0].g,
149
+ );
150
+ })();
151
+
152
+ const numAtom = atom(0);
153
+
154
+ const inputValueAtom = atom('');
155
+
156
+ function App() {
157
+ const test = useAtomValue(testAtom);
158
+ const testText = useAtomValue(testTextAtom);
159
+ const testDo = useAtomDo(testAtom);
160
+ const value = useAtomValue(inputValueAtom);
161
+ console.log({ num: useAtomValue(numAtom) });
162
+
163
+ console.info(test);
164
+
165
+ useEffect(() => {
166
+ const onClick = () => {
167
+ testDo.add(Date.now());
168
+ testDo.update12();
169
+ testTextAtom.do.addText('1');
170
+
171
+ numAtom.set(num => {
172
+ console.log(num);
173
+ return 1;
174
+ });
175
+ numAtom.set(3);
176
+ numAtom.set(num => {
177
+ console.log(num);
178
+ return 4;
179
+ });
180
+ numAtom.set(num => {
181
+ console.log(num);
182
+ return 5;
183
+ });
184
+ numAtom.set(6);
185
+ numAtom.set(num => {
186
+ console.log(num);
187
+ return 7;
188
+ });
189
+ };
190
+
191
+ window.addEventListener('click', onClick);
192
+ return () => window.removeEventListener('click', onClick);
193
+ }, []);
194
+
195
+ return (
196
+ <>
197
+ {testText}
198
+ <input
199
+ value={value}
200
+ onChange={event => {
201
+ inputValueAtom.set(event.currentTarget.value + '*');
202
+ inputValueAtom.set(event.currentTarget.value);
203
+ }}
204
+ />
205
+ </>
206
+ );
207
+ }
package/types/index.d.ts CHANGED
@@ -3,6 +3,12 @@ import { Path, PathValue, PathValueDonor } from './paths';
3
3
 
4
4
  export interface Register {}
5
5
 
6
+ export type ObjectActionsSetDeepPartial = Register extends {
7
+ keyPathSeparator: infer Separator extends string;
8
+ }
9
+ ? Separator
10
+ : '.';
11
+
6
12
  type Sunscriber<Value> = (value: Value) => void;
7
13
 
8
14
  export type AtomStoreKey = `${string}${string}:${string}${string}`;
@@ -78,12 +84,6 @@ export type ObjectActions<Value> = UpdateAction<Value> & {
78
84
  ) => void;
79
85
  };
80
86
 
81
- export type ObjectActionsSetDeepPartial = Register extends {
82
- keyPathSeparator: infer Separator extends string;
83
- }
84
- ? Separator
85
- : '.';
86
-
87
87
  export type BooleanActions = {
88
88
  /** toggle current value between true/false */
89
89
  toggle: () => void;
package/types/paths.ts CHANGED
@@ -85,9 +85,9 @@ export type PathValueDonor<
85
85
  ? Required<Record<Key, PathValueDonor<Value[Key], Sep, KeyRest>>>
86
86
  : never
87
87
  : Value extends ReadonlyArray<infer V>
88
- ? [PathValueDonor<V, Sep, KeyRest & Path<V, Sep>> | V]
88
+ ? [PathValueDonor<V, Sep, KeyRest & Path<V, Sep>>]
89
89
  : Value extends Partial<Record<infer K, infer V>> | Record<infer K, infer V>
90
- ? Record<K, PathValueDonor<V, Sep, KeyRest & Path<V, Sep>>> | Value
90
+ ? Record<K, PathValueDonor<V, Sep, KeyRest & Path<V, Sep>>>
91
91
  : never
92
92
  : FullPath extends keyof Value
93
93
  ? FullPath extends `${string}${Sep}${string}${string}`
@@ -100,7 +100,7 @@ export type PathValueDonor<
100
100
  ? [V]
101
101
  : []
102
102
  : Value extends Partial<Record<infer K, infer V>> | Record<infer K, infer V>
103
- ? Record<K, V> | Value
103
+ ? Record<K, V>
104
104
  : never
105
105
  : never;
106
106