UNPKG

1.95 kBJavaScriptView Raw
1import * as O from 'optics-ts';
2import { atom } from 'jotai';
3
4const getWeakCacheItem = (cache, deps) => {
5 do {
6 const [dep, ...rest] = deps;
7 const entry = cache.get(dep);
8 if (!entry) {
9 return;
10 }
11 if (!rest.length) {
12 return entry[1];
13 }
14 cache = entry[0];
15 deps = rest;
16 } while (deps.length);
17};
18const setWeakCacheItem = (cache, deps, item) => {
19 do {
20 const [dep, ...rest] = deps;
21 let entry = cache.get(dep);
22 if (!entry) {
23 entry = [ new WeakMap()];
24 cache.set(dep, entry);
25 }
26 if (!rest.length) {
27 entry[1] = item;
28 return;
29 }
30 cache = entry[0];
31 deps = rest;
32 } while (deps.length);
33};
34const createMemoizeAtom = () => {
35 const cache = /* @__PURE__ */ new WeakMap();
36 const memoizeAtom = (createAtom, deps) => {
37 const cachedAtom = getWeakCacheItem(cache, deps);
38 if (cachedAtom) {
39 return cachedAtom;
40 }
41 const createdAtom = createAtom();
42 setWeakCacheItem(cache, deps, createdAtom);
43 return createdAtom;
44 };
45 return memoizeAtom;
46};
47
48const memoizeAtom = createMemoizeAtom();
49const isFunction = (x) => typeof x === "function";
50function focusAtom(baseAtom, callback) {
51 return memoizeAtom(() => {
52 const focus = callback(O.optic());
53 const derivedAtom = atom(
54 (get) => getValueUsingOptic(focus, get(baseAtom)),
55 (get, set, update) => {
56 const newValueProducer = isFunction(update) ? O.modify(focus)(update) : O.set(focus)(update);
57 return set(baseAtom, newValueProducer(get(baseAtom)));
58 }
59 );
60 return derivedAtom;
61 }, [baseAtom, callback]);
62}
63const getValueUsingOptic = (focus, bigValue) => {
64 if (focus._tag === "Traversal") {
65 const values = O.collect(focus)(bigValue);
66 return values;
67 }
68 if (focus._tag === "Prism") {
69 const value2 = O.preview(focus)(bigValue);
70 return value2;
71 }
72 const value = O.get(focus)(bigValue);
73 return value;
74};
75
76export { focusAtom };