@legendapp/state 3.0.0-beta.3 → 3.0.0-beta.30

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.
Files changed (74) hide show
  1. package/.DS_Store +0 -0
  2. package/config/enableReactComponents.js +3 -1
  3. package/config/enableReactComponents.mjs +3 -1
  4. package/config/enableReactTracking.d.mts +2 -1
  5. package/config/enableReactTracking.d.ts +2 -1
  6. package/config/enableReactTracking.js +32 -13
  7. package/config/enableReactTracking.mjs +32 -13
  8. package/index.d.mts +33 -4
  9. package/index.d.ts +33 -4
  10. package/index.js +191 -29
  11. package/index.mjs +191 -29
  12. package/package.json +35 -1
  13. package/persist-plugins/async-storage.js +17 -9
  14. package/persist-plugins/async-storage.mjs +17 -9
  15. package/persist-plugins/expo-sqlite.d.mts +19 -0
  16. package/persist-plugins/expo-sqlite.d.ts +19 -0
  17. package/persist-plugins/expo-sqlite.js +72 -0
  18. package/persist-plugins/expo-sqlite.mjs +69 -0
  19. package/react-native.d.mts +4 -0
  20. package/react-native.d.ts +4 -0
  21. package/react-native.js +53 -0
  22. package/react-native.mjs +40 -0
  23. package/react-reactive/Components.d.mts +19 -0
  24. package/react-reactive/Components.d.ts +19 -0
  25. package/react-reactive/Components.js +53 -0
  26. package/react-reactive/Components.mjs +40 -0
  27. package/react-reactive/enableReactComponents.d.mts +3 -2
  28. package/react-reactive/enableReactComponents.d.ts +3 -2
  29. package/react-reactive/enableReactComponents.js +10 -3
  30. package/react-reactive/enableReactComponents.mjs +10 -3
  31. package/react-reactive/enableReactNativeComponents.d.mts +3 -20
  32. package/react-reactive/enableReactNativeComponents.d.ts +3 -20
  33. package/react-reactive/enableReactNativeComponents.js +8 -3
  34. package/react-reactive/enableReactNativeComponents.mjs +8 -3
  35. package/react-reactive/enableReactive.js +10 -3
  36. package/react-reactive/enableReactive.mjs +10 -3
  37. package/react-reactive/enableReactive.native.js +8 -3
  38. package/react-reactive/enableReactive.native.mjs +8 -3
  39. package/react-reactive/enableReactive.web.js +8 -3
  40. package/react-reactive/enableReactive.web.mjs +8 -3
  41. package/react-web.d.mts +6 -0
  42. package/react-web.d.ts +6 -0
  43. package/react-web.js +39 -0
  44. package/react-web.mjs +37 -0
  45. package/react.d.mts +41 -21
  46. package/react.d.ts +41 -21
  47. package/react.js +36 -23
  48. package/react.mjs +37 -25
  49. package/sync-plugins/crud.d.mts +24 -9
  50. package/sync-plugins/crud.d.ts +24 -9
  51. package/sync-plugins/crud.js +250 -116
  52. package/sync-plugins/crud.mjs +251 -117
  53. package/sync-plugins/firebase.d.mts +7 -3
  54. package/sync-plugins/firebase.d.ts +7 -3
  55. package/sync-plugins/firebase.js +4 -2
  56. package/sync-plugins/firebase.mjs +4 -2
  57. package/sync-plugins/keel.d.mts +12 -13
  58. package/sync-plugins/keel.d.ts +12 -13
  59. package/sync-plugins/keel.js +60 -52
  60. package/sync-plugins/keel.mjs +61 -48
  61. package/sync-plugins/supabase.d.mts +7 -3
  62. package/sync-plugins/supabase.d.ts +7 -3
  63. package/sync-plugins/supabase.js +90 -33
  64. package/sync-plugins/supabase.mjs +91 -34
  65. package/sync-plugins/tanstack-query.d.mts +3 -3
  66. package/sync-plugins/tanstack-query.d.ts +3 -3
  67. package/sync.d.mts +16 -8
  68. package/sync.d.ts +16 -8
  69. package/sync.js +324 -215
  70. package/sync.mjs +323 -215
  71. package/trace.js +5 -6
  72. package/trace.mjs +5 -6
  73. package/types/reactive-native.d.ts +19 -0
  74. package/types/reactive-web.d.ts +7 -0
package/index.mjs CHANGED
@@ -179,7 +179,7 @@ function setNodeValue(node, newValue) {
179
179
  parentNode.isSetting--;
180
180
  }
181
181
  }
182
- return { prevValue, newValue };
182
+ return { prevValue, newValue, parentValue };
183
183
  }
184
184
  var arrNodeKeys = [];
185
185
  function getNodeValue(node) {
@@ -255,6 +255,9 @@ function extractFunction(node, key, fnOrComputed) {
255
255
  function equals(a, b) {
256
256
  return a === b || isDate(a) && isDate(b) && +a === +b;
257
257
  }
258
+ function getKeys(obj, isArr, isMap2, isSet2) {
259
+ return isArr ? void 0 : obj ? isSet2 ? Array.from(obj) : isMap2 ? Array.from(obj.keys()) : Object.keys(obj) : [];
260
+ }
258
261
 
259
262
  // src/ObservableHint.ts
260
263
  function addSymbol(value, symbol) {
@@ -274,16 +277,19 @@ var ObservableHint = {
274
277
  },
275
278
  plain: function plainObject(value) {
276
279
  return addSymbol(value, symbolPlain);
280
+ },
281
+ function: function plainObject2(value) {
282
+ return addSymbol(value, symbolPlain);
277
283
  }
278
284
  };
279
285
 
280
286
  // src/helpers.ts
281
- function computeSelector(selector, e, retainObservable) {
287
+ function computeSelector(selector, getOptions, e, retainObservable) {
282
288
  let c = selector;
283
289
  if (!isObservable(c) && isFunction(c)) {
284
290
  c = e ? c(e) : c();
285
291
  }
286
- return isObservable(c) && !retainObservable ? c.get() : c;
292
+ return isObservable(c) && !retainObservable ? c.get(getOptions) : c;
287
293
  }
288
294
  function getObservableIndex(value$) {
289
295
  const node = getNode(value$);
@@ -382,7 +388,7 @@ function _mergeIntoObservable(target, source, levelsDeep) {
382
388
  const isSourceSet = isSet(source);
383
389
  if (isSourceSet && isSet(targetValue)) {
384
390
  target.set(/* @__PURE__ */ new Set([...source, ...targetValue]));
385
- } else if (isTargetObj && isObject(source) && !isEmpty(targetValue) || isTargetArr && targetValue.length > 0) {
391
+ } else if (isTargetObj && isObject(source) || isTargetArr && targetValue.length > 0) {
386
392
  const keys = isSourceMap || isSourceSet ? Array.from(source.keys()) : Object.keys(source);
387
393
  for (let i = 0; i < keys.length; i++) {
388
394
  const key = keys[i];
@@ -588,6 +594,7 @@ function computeChangesAtNode(changesInBatch, node, isFromPersist, isFromSync, v
588
594
  if (!isArraySubset(changes[0].path, change.path)) {
589
595
  changes.push(change);
590
596
  changeInBatch.level = Math.min(changeInBatch.level, level);
597
+ changeInBatch.whenOptimizedOnlyIf || (changeInBatch.whenOptimizedOnlyIf = whenOptimizedOnlyIf);
591
598
  }
592
599
  } else {
593
600
  changesInBatch.set(node, {
@@ -809,6 +816,109 @@ function linked(params, options) {
809
816
  return ret;
810
817
  }
811
818
 
819
+ // src/middleware.ts
820
+ var nodeMiddlewareHandlers = /* @__PURE__ */ new WeakMap();
821
+ var queuedNodes = [];
822
+ var queuedListeners = [];
823
+ var queuedTypes = [];
824
+ var queueSize = 0;
825
+ var isMicrotaskScheduled = false;
826
+ function registerMiddleware(node, type, handler) {
827
+ let handlersMap = nodeMiddlewareHandlers.get(node);
828
+ if (!handlersMap) {
829
+ handlersMap = /* @__PURE__ */ new Map();
830
+ nodeMiddlewareHandlers.set(node, handlersMap);
831
+ }
832
+ let handlers = handlersMap.get(type);
833
+ if (!handlers) {
834
+ handlers = /* @__PURE__ */ new Set();
835
+ handlersMap.set(type, handlers);
836
+ }
837
+ handlers.add(handler);
838
+ return () => {
839
+ const handlersMap2 = nodeMiddlewareHandlers.get(node);
840
+ if (!handlersMap2)
841
+ return;
842
+ const handlers2 = handlersMap2.get(type);
843
+ if (!handlers2)
844
+ return;
845
+ handlers2.delete(handler);
846
+ if (handlers2.size === 0) {
847
+ handlersMap2.delete(type);
848
+ if (handlersMap2.size === 0) {
849
+ nodeMiddlewareHandlers.delete(node);
850
+ }
851
+ }
852
+ };
853
+ }
854
+ function dispatchMiddlewareEvent(node, listener, type) {
855
+ const handlersMap = nodeMiddlewareHandlers.get(node);
856
+ if (!handlersMap || !handlersMap.has(type)) {
857
+ return;
858
+ }
859
+ const handlers = handlersMap.get(type);
860
+ if (!handlers || handlers.size === 0) {
861
+ return;
862
+ }
863
+ queuedNodes[queueSize] = node;
864
+ queuedListeners[queueSize] = listener;
865
+ queuedTypes[queueSize] = type;
866
+ queueSize++;
867
+ if (!isMicrotaskScheduled) {
868
+ isMicrotaskScheduled = true;
869
+ queueMicrotask(processQueuedEvents);
870
+ }
871
+ }
872
+ var eventObj = {
873
+ type: "listener-added",
874
+ node: null,
875
+ listener: void 0,
876
+ timestamp: 0
877
+ };
878
+ function processQueuedEvents() {
879
+ isMicrotaskScheduled = false;
880
+ const timestamp = typeof performance !== "undefined" ? performance.now() : Date.now();
881
+ eventObj.timestamp = timestamp;
882
+ for (let i = 0; i < queueSize; i++) {
883
+ const node = queuedNodes[i];
884
+ const listener = queuedListeners[i];
885
+ const type = queuedTypes[i];
886
+ const handlersMap = nodeMiddlewareHandlers.get(node);
887
+ if (!handlersMap)
888
+ continue;
889
+ const handlers = handlersMap.get(type);
890
+ if (!handlers || handlers.size === 0)
891
+ continue;
892
+ const nodeListeners = node.listeners;
893
+ const nodeListenersImmediate = node.listenersImmediate;
894
+ if (!nodeListeners && !nodeListenersImmediate) {
895
+ continue;
896
+ }
897
+ let isValid = false;
898
+ if (type === "listener-added") {
899
+ isValid = !!(nodeListeners == null ? void 0 : nodeListeners.has(listener)) || !!(nodeListenersImmediate == null ? void 0 : nodeListenersImmediate.has(listener));
900
+ } else if (type === "listener-removed") {
901
+ isValid = !(nodeListeners == null ? void 0 : nodeListeners.has(listener)) && !(nodeListenersImmediate == null ? void 0 : nodeListenersImmediate.has(listener));
902
+ } else {
903
+ isValid = !(nodeListeners == null ? void 0 : nodeListeners.size) && !(nodeListenersImmediate == null ? void 0 : nodeListenersImmediate.size);
904
+ }
905
+ if (isValid) {
906
+ eventObj.type = type;
907
+ eventObj.node = node;
908
+ eventObj.listener = listener;
909
+ const iterableHandlers = Array.from(handlers);
910
+ for (let j = 0; j < iterableHandlers.length; j++) {
911
+ try {
912
+ iterableHandlers[j](eventObj);
913
+ } catch (error) {
914
+ console.error(`Error in middleware handler for ${type}:`, error);
915
+ }
916
+ }
917
+ }
918
+ }
919
+ queueSize = 0;
920
+ }
921
+
812
922
  // src/onChange.ts
813
923
  function onChange(node, callback, options = {}, fromLinks) {
814
924
  var _a;
@@ -879,6 +989,7 @@ function onChange(node, callback, options = {}, fromLinks) {
879
989
  pathParent = [parent.key, ...pathParent];
880
990
  parent = parent.parent;
881
991
  }
992
+ dispatchMiddlewareEvent(node, listener, "listener-added");
882
993
  return () => {
883
994
  listeners.delete(listener);
884
995
  extraDisposes == null ? void 0 : extraDisposes.forEach((fn) => fn());
@@ -887,6 +998,10 @@ function onChange(node, callback, options = {}, fromLinks) {
887
998
  parent2.numListenersRecursive--;
888
999
  parent2 = parent2.parent;
889
1000
  }
1001
+ dispatchMiddlewareEvent(node, listener, "listener-removed");
1002
+ if (listeners.size === 0) {
1003
+ dispatchMiddlewareEvent(node, void 0, "listeners-cleared");
1004
+ }
890
1005
  };
891
1006
  }
892
1007
  function createCb(linkedFromNode, path, callback) {
@@ -967,13 +1082,13 @@ function updateTracking(node, track) {
967
1082
  }
968
1083
 
969
1084
  // src/trackSelector.ts
970
- function trackSelector(selector, update, observeEvent, observeOptions, createResubscribe) {
1085
+ function trackSelector(selector, update, getOptions, observeEvent, observeOptions, createResubscribe) {
971
1086
  var _a;
972
1087
  let dispose;
973
1088
  let resubscribe;
974
1089
  let updateFn = update;
975
1090
  beginTracking();
976
- const value = selector ? computeSelector(selector, observeEvent, observeOptions == null ? void 0 : observeOptions.fromComputed) : selector;
1091
+ const value = selector ? computeSelector(selector, getOptions, observeEvent, observeOptions == null ? void 0 : observeOptions.fromComputed) : selector;
977
1092
  const tracker = tracking.current;
978
1093
  const nodes = tracker.nodes;
979
1094
  endTracking();
@@ -1021,7 +1136,11 @@ function observe(selectorOrRun, reactionOrOptions, options) {
1021
1136
  beginBatch();
1022
1137
  delete e.value;
1023
1138
  dispose == null ? void 0 : dispose();
1024
- const { dispose: _dispose, value, nodes } = trackSelector(selectorOrRun, update, e, options);
1139
+ const {
1140
+ dispose: _dispose,
1141
+ value,
1142
+ nodes
1143
+ } = trackSelector(selectorOrRun, update, void 0, e, options);
1025
1144
  dispose = _dispose;
1026
1145
  e.value = value;
1027
1146
  e.nodes = nodes;
@@ -1066,10 +1185,13 @@ function _when(predicate, effect, checkReady) {
1066
1185
  let isOk = true;
1067
1186
  if (isArray(ret)) {
1068
1187
  for (let i = 0; i < ret.length; i++) {
1069
- if (isObservable(ret[i])) {
1070
- ret[i] = computeSelector(ret[i]);
1188
+ let item = ret[i];
1189
+ if (isObservable(item)) {
1190
+ item = computeSelector(item);
1191
+ } else if (isFunction(item)) {
1192
+ item = item();
1071
1193
  }
1072
- isOk = isOk && !!(checkReady ? isObservableValueReady(ret[i]) : ret[i]);
1194
+ isOk = isOk && !!(checkReady ? isObservableValueReady(item) : item);
1073
1195
  }
1074
1196
  } else {
1075
1197
  isOk = checkReady ? isObservableValueReady(ret) : ret;
@@ -1168,9 +1290,6 @@ function collectionSetter(node, target, prop, ...args) {
1168
1290
  return ret;
1169
1291
  }
1170
1292
  }
1171
- function getKeys(obj, isArr, isMap2) {
1172
- return isArr ? void 0 : obj ? isMap2 ? Array.from(obj.keys()) : Object.keys(obj) : [];
1173
- }
1174
1293
  function updateNodes(parent, obj, prevValue) {
1175
1294
  var _a, _b, _c;
1176
1295
  if ((process.env.NODE_ENV === "development" || process.env.NODE_ENV === "test") && typeof __devUpdateNodes !== "undefined" && isObject(obj)) {
@@ -1199,9 +1318,11 @@ function updateNodes(parent, obj, prevValue) {
1199
1318
  let prevChildrenById;
1200
1319
  let moved;
1201
1320
  const isCurMap = isMap(obj);
1321
+ const isCurSet = isSet(obj);
1202
1322
  const isPrevMap = isMap(prevValue);
1203
- const keys = getKeys(obj, isArr, isCurMap);
1204
- const keysPrev = getKeys(prevValue, isArr, isPrevMap);
1323
+ const isPrevSet = isSet(prevValue);
1324
+ const keys = getKeys(obj, isArr, isCurMap, isCurSet);
1325
+ const keysPrev = getKeys(prevValue, isArr, isPrevMap, isPrevSet);
1205
1326
  const length = ((_a = keys || obj) == null ? void 0 : _a.length) || 0;
1206
1327
  const lengthPrev = ((_b = keysPrev || prevValue) == null ? void 0 : _b.length) || 0;
1207
1328
  let idField;
@@ -1551,7 +1672,9 @@ var proxyHandler = {
1551
1672
  if (isObservable(thisArg)) {
1552
1673
  thisArg = thisArg.peek();
1553
1674
  }
1554
- return Reflect.apply(target.lazyFn || target, thisArg, argArray);
1675
+ const fnRaw = getNodeValue(target);
1676
+ const fn = isFunction(fnRaw) ? fnRaw : target.lazyFn || target;
1677
+ return Reflect.apply(fn, thisArg, argArray);
1555
1678
  }
1556
1679
  };
1557
1680
  function set(node, newValue) {
@@ -1583,8 +1706,8 @@ function setKey(node, key, newValue, level) {
1583
1706
  if (isObservable(newValue)) {
1584
1707
  setToObservable(childNode, newValue);
1585
1708
  } else {
1586
- const { newValue: savedValue, prevValue } = setNodeValue(childNode, newValue);
1587
- const isPrim = isPrimitive(savedValue) || savedValue instanceof Date;
1709
+ const { newValue: savedValue, prevValue, parentValue } = setNodeValue(childNode, newValue);
1710
+ const isPrim = isPrimitive(prevValue) || prevValue instanceof Date || isPrimitive(savedValue) || savedValue instanceof Date;
1588
1711
  if (!isPrim) {
1589
1712
  let parent = childNode;
1590
1713
  do {
@@ -1595,7 +1718,17 @@ function setKey(node, key, newValue, level) {
1595
1718
  const notify2 = !equals(savedValue, prevValue);
1596
1719
  const forceNotify = !notify2 && childNode.isComputing && !isPrim;
1597
1720
  if (notify2 || forceNotify) {
1598
- updateNodesAndNotify(node, savedValue, prevValue, childNode, isPrim, isRoot, level, forceNotify);
1721
+ updateNodesAndNotify(
1722
+ node,
1723
+ savedValue,
1724
+ prevValue,
1725
+ childNode,
1726
+ parentValue,
1727
+ isPrim,
1728
+ isRoot,
1729
+ level,
1730
+ forceNotify
1731
+ );
1599
1732
  }
1600
1733
  extractFunctionOrComputed(node, key, savedValue);
1601
1734
  }
@@ -1650,7 +1783,7 @@ function handlerMapSet(node, p, value) {
1650
1783
  } else if (isFunction(vProp)) {
1651
1784
  return function(a, b, c) {
1652
1785
  const l = arguments.length;
1653
- const valueMap = value;
1786
+ const valueMapOrSet = value;
1654
1787
  if (p === "get") {
1655
1788
  if (l > 0 && typeof a !== "boolean" && a !== optimized) {
1656
1789
  return getProxy(node, a);
@@ -1664,14 +1797,14 @@ function handlerMapSet(node, p, value) {
1664
1797
  return getProxy(node);
1665
1798
  } else if (p === "delete") {
1666
1799
  if (l > 0) {
1667
- const prev = value.get ? valueMap.get(a) : a;
1800
+ const prev = value.get ? valueMapOrSet.get(a) : a;
1668
1801
  deleteFn(node, a);
1669
1802
  return prev !== void 0;
1670
1803
  }
1671
1804
  } else if (p === "clear") {
1672
- const prev = new Map(valueMap);
1673
- const size = valueMap.size;
1674
- valueMap.clear();
1805
+ const prev = isSet(valueMapOrSet) ? new Set(valueMapOrSet) : new Map(valueMapOrSet);
1806
+ const size = valueMapOrSet.size;
1807
+ valueMapOrSet.clear();
1675
1808
  if (size) {
1676
1809
  updateNodesAndNotify(node, value, prev);
1677
1810
  }
@@ -1702,7 +1835,7 @@ function handlerMapSet(node, p, value) {
1702
1835
  };
1703
1836
  }
1704
1837
  }
1705
- function updateNodesAndNotify(node, newValue, prevValue, childNode, isPrim, isRoot, level, forceNotify) {
1838
+ function updateNodesAndNotify(node, newValue, prevValue, childNode, parentValue, isPrim, isRoot, level, forceNotify) {
1706
1839
  if (!childNode)
1707
1840
  childNode = node;
1708
1841
  beginBatch();
@@ -1711,15 +1844,29 @@ function updateNodesAndNotify(node, newValue, prevValue, childNode, isPrim, isRo
1711
1844
  }
1712
1845
  let hasADiff = forceNotify || isPrim;
1713
1846
  let whenOptimizedOnlyIf = false;
1847
+ let valueAsArr;
1848
+ let valueAsMap;
1714
1849
  if (!isPrim || prevValue && !isPrimitive(prevValue)) {
1715
1850
  if ((process.env.NODE_ENV === "development" || process.env.NODE_ENV === "test") && typeof __devUpdateNodes !== "undefined") {
1716
1851
  __devUpdateNodes.clear();
1717
1852
  }
1718
1853
  hasADiff = hasADiff || updateNodes(childNode, newValue, prevValue);
1719
1854
  if (isArray(newValue)) {
1720
- whenOptimizedOnlyIf = (newValue == null ? void 0 : newValue.length) !== (prevValue == null ? void 0 : prevValue.length);
1855
+ valueAsArr = newValue;
1856
+ } else if (isMap(newValue) || isSet(newValue)) {
1857
+ valueAsMap = newValue;
1721
1858
  }
1722
1859
  }
1860
+ if (isArray(parentValue)) {
1861
+ valueAsArr = parentValue;
1862
+ } else if (isMap(parentValue) || isSet(parentValue)) {
1863
+ valueAsMap = parentValue;
1864
+ }
1865
+ if (valueAsArr) {
1866
+ whenOptimizedOnlyIf = (valueAsArr == null ? void 0 : valueAsArr.length) !== (prevValue == null ? void 0 : prevValue.length);
1867
+ } else if (valueAsMap) {
1868
+ whenOptimizedOnlyIf = (valueAsMap == null ? void 0 : valueAsMap.size) !== (prevValue == null ? void 0 : prevValue.size);
1869
+ }
1723
1870
  if (isPrim || !newValue || isEmpty(newValue) && !isEmpty(prevValue) ? newValue !== prevValue : hasADiff) {
1724
1871
  notify(
1725
1872
  isPrim && isRoot ? node : childNode,
@@ -1786,7 +1933,7 @@ function peek(node) {
1786
1933
  }
1787
1934
  var isFlushing = false;
1788
1935
  function peekInternal(node, activateRecursive) {
1789
- var _a;
1936
+ var _a, _b;
1790
1937
  isFlushing = true;
1791
1938
  if (activateRecursive && ((_a = node.dirtyChildren) == null ? void 0 : _a.size)) {
1792
1939
  const dirty = Array.from(node.dirtyChildren);
@@ -1801,7 +1948,10 @@ function peekInternal(node, activateRecursive) {
1801
1948
  }
1802
1949
  isFlushing = false;
1803
1950
  let value = getNodeValue(node);
1804
- if (!globalState.isLoadingLocal) {
1951
+ if (((_b = node.parent) == null ? void 0 : _b.isPlain) || isHintPlain(value)) {
1952
+ node.isPlain = true;
1953
+ }
1954
+ if (!node.root.isLoadingLocal && !node.isPlain) {
1805
1955
  value = checkLazy(node, value, !!activateRecursive);
1806
1956
  }
1807
1957
  return value;
@@ -1961,6 +2111,9 @@ function activateNodeFunction(node, lazyFn) {
1961
2111
  value = (_d = (_c = activated2.get) == null ? void 0 : _c.call(activated2)) != null ? _d : activated2.initial;
1962
2112
  }
1963
2113
  }
2114
+ if (ignoreThisUpdate) {
2115
+ activatedValue = value;
2116
+ }
1964
2117
  wasPromise = wasPromise || isPromise(value);
1965
2118
  return value;
1966
2119
  },
@@ -2272,7 +2425,14 @@ function syncState(obs) {
2272
2425
  syncCount: 0,
2273
2426
  resetPersistence: void 0,
2274
2427
  reset: () => Promise.resolve(),
2275
- sync: () => Promise.resolve(),
2428
+ sync: () => {
2429
+ var _a;
2430
+ obs.peek();
2431
+ if ((_a = node.state) == null ? void 0 : _a.isGetting.peek()) {
2432
+ return when(node.state.isLoaded);
2433
+ }
2434
+ return Promise.resolve();
2435
+ },
2276
2436
  getPendingChanges: () => ({}),
2277
2437
  // TODOV3 remove
2278
2438
  clearPersist: void 0
@@ -2290,6 +2450,7 @@ var internal = {
2290
2450
  ensureNodeValue,
2291
2451
  findIDKey,
2292
2452
  get,
2453
+ getKeys,
2293
2454
  getNode,
2294
2455
  getNodeValue,
2295
2456
  getPathType,
@@ -2302,6 +2463,7 @@ var internal = {
2302
2463
  observableFns,
2303
2464
  optimized,
2304
2465
  peek,
2466
+ registerMiddleware,
2305
2467
  safeParse,
2306
2468
  safeStringify,
2307
2469
  set,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@legendapp/state",
3
- "version": "3.0.0-beta.3",
3
+ "version": "3.0.0-beta.30",
4
4
  "description": "legend-state",
5
5
  "sideEffects": false,
6
6
  "private": false,
@@ -13,6 +13,14 @@
13
13
  "dependencies": {
14
14
  "use-sync-external-store": "^1.2.2"
15
15
  },
16
+ "peerDependencies": {
17
+ "expo-sqlite": "^15.0.0"
18
+ },
19
+ "peerDependenciesMeta": {
20
+ "expo-sqlite": {
21
+ "optional": true
22
+ }
23
+ },
16
24
  "author": "Legend <contact@legendapp.com> (https://github.com/LegendApp)",
17
25
  "keywords": [
18
26
  "react",
@@ -48,6 +56,12 @@
48
56
  "./types/babel": {
49
57
  "types": "./types/babel.d.ts"
50
58
  },
59
+ "./types/reactive-web": {
60
+ "types": "./types/reactive-web.d.ts"
61
+ },
62
+ "./types/reactive-native": {
63
+ "types": "./types/reactive-native.d.ts"
64
+ },
51
65
  ".": {
52
66
  "import": "./index.mjs",
53
67
  "require": "./index.js",
@@ -63,6 +77,16 @@
63
77
  "require": "./react.js",
64
78
  "types": "./react.d.ts"
65
79
  },
80
+ "./react-native": {
81
+ "import": "./react-native.mjs",
82
+ "require": "./react-native.js",
83
+ "types": "./react-native.d.ts"
84
+ },
85
+ "./react-web": {
86
+ "import": "./react-web.mjs",
87
+ "require": "./react-web.js",
88
+ "types": "./react-web.d.ts"
89
+ },
66
90
  "./trace": {
67
91
  "import": "./trace.mjs",
68
92
  "require": "./trace.js",
@@ -73,6 +97,11 @@
73
97
  "require": "./react-reactive/enableReactive.js",
74
98
  "types": "./react-reactive/enableReactive.d.ts"
75
99
  },
100
+ "./react-reactive/Components": {
101
+ "import": "./react-reactive/Components.mjs",
102
+ "require": "./react-reactive/Components.js",
103
+ "types": "./react-reactive/Components.d.ts"
104
+ },
76
105
  "./react-reactive/enableReactComponents": {
77
106
  "import": "./react-reactive/enableReactComponents.mjs",
78
107
  "require": "./react-reactive/enableReactComponents.js",
@@ -228,6 +257,11 @@
228
257
  "require": "./persist-plugins/local-storage.js",
229
258
  "types": "./persist-plugins/local-storage.d.ts"
230
259
  },
260
+ "./persist-plugins/expo-sqlite": {
261
+ "import": "./persist-plugins/expo-sqlite.mjs",
262
+ "require": "./persist-plugins/expo-sqlite.js",
263
+ "types": "./persist-plugins/expo-sqlite.d.ts"
264
+ },
231
265
  "./persist-plugins/async-storage": {
232
266
  "import": "./persist-plugins/async-storage.mjs",
233
267
  "require": "./persist-plugins/async-storage.js",
@@ -21,7 +21,10 @@ var ObservablePersistAsyncStorage = class {
21
21
  if (preload === true) {
22
22
  tables = await AsyncStorage.getAllKeys();
23
23
  } else if (state.isArray(preload)) {
24
- tables = preload;
24
+ const metadataTables = preload.map(
25
+ (table) => table.endsWith(MetadataSuffix) ? void 0 : table + MetadataSuffix
26
+ );
27
+ tables = [...preload, ...metadataTables.filter(Boolean)];
25
28
  }
26
29
  if (tables) {
27
30
  const values = await AsyncStorage.multiGet(tables);
@@ -38,14 +41,19 @@ var ObservablePersistAsyncStorage = class {
38
41
  }
39
42
  loadTable(table) {
40
43
  if (this.data[table] === void 0) {
41
- try {
42
- return (async () => {
43
- const value = await AsyncStorage.getItem(table);
44
- this.data[table] = value ? safeParse(value) : void 0;
45
- })();
46
- } catch (e) {
47
- console.error("[legend-state] ObservablePersistLocalAsyncStorage failed to parse", table);
48
- }
44
+ return AsyncStorage.multiGet([table, table + MetadataSuffix]).then((values) => {
45
+ try {
46
+ values.forEach(([table2, value]) => {
47
+ this.data[table2] = value ? safeParse(value) : void 0;
48
+ });
49
+ } catch (err) {
50
+ console.error("[legend-state] ObservablePersistLocalAsyncStorage failed to parse", table, err);
51
+ }
52
+ }).catch((err) => {
53
+ if ((err == null ? void 0 : err.message) !== "window is not defined") {
54
+ console.error("[legend-state] AsyncStorage.multiGet failed", table, err);
55
+ }
56
+ });
49
57
  }
50
58
  }
51
59
  // Gets
@@ -19,7 +19,10 @@ var ObservablePersistAsyncStorage = class {
19
19
  if (preload === true) {
20
20
  tables = await AsyncStorage.getAllKeys();
21
21
  } else if (isArray(preload)) {
22
- tables = preload;
22
+ const metadataTables = preload.map(
23
+ (table) => table.endsWith(MetadataSuffix) ? void 0 : table + MetadataSuffix
24
+ );
25
+ tables = [...preload, ...metadataTables.filter(Boolean)];
23
26
  }
24
27
  if (tables) {
25
28
  const values = await AsyncStorage.multiGet(tables);
@@ -36,14 +39,19 @@ var ObservablePersistAsyncStorage = class {
36
39
  }
37
40
  loadTable(table) {
38
41
  if (this.data[table] === void 0) {
39
- try {
40
- return (async () => {
41
- const value = await AsyncStorage.getItem(table);
42
- this.data[table] = value ? safeParse(value) : void 0;
43
- })();
44
- } catch (e) {
45
- console.error("[legend-state] ObservablePersistLocalAsyncStorage failed to parse", table);
46
- }
42
+ return AsyncStorage.multiGet([table, table + MetadataSuffix]).then((values) => {
43
+ try {
44
+ values.forEach(([table2, value]) => {
45
+ this.data[table2] = value ? safeParse(value) : void 0;
46
+ });
47
+ } catch (err) {
48
+ console.error("[legend-state] ObservablePersistLocalAsyncStorage failed to parse", table, err);
49
+ }
50
+ }).catch((err) => {
51
+ if ((err == null ? void 0 : err.message) !== "window is not defined") {
52
+ console.error("[legend-state] AsyncStorage.multiGet failed", table, err);
53
+ }
54
+ });
47
55
  }
48
56
  }
49
57
  // Gets
@@ -0,0 +1,19 @@
1
+ import { Change } from '@legendapp/state';
2
+ import { ObservablePersistPlugin, PersistMetadata } from '@legendapp/state/sync';
3
+ import { SQLiteStorage } from 'expo-sqlite/kv-store';
4
+
5
+ declare class ObservablePersistSqlite implements ObservablePersistPlugin {
6
+ private data;
7
+ private storage;
8
+ constructor(storage: SQLiteStorage);
9
+ getTable(table: string, init: any): any;
10
+ getMetadata(table: string): PersistMetadata;
11
+ set(table: string, changes: Change[]): void;
12
+ setMetadata(table: string, metadata: PersistMetadata): void;
13
+ deleteTable(table: string): undefined;
14
+ deleteMetadata(table: string): void;
15
+ private save;
16
+ }
17
+ declare function observablePersistSqlite(storage: SQLiteStorage): ObservablePersistSqlite;
18
+
19
+ export { ObservablePersistSqlite, observablePersistSqlite };
@@ -0,0 +1,19 @@
1
+ import { Change } from '@legendapp/state';
2
+ import { ObservablePersistPlugin, PersistMetadata } from '@legendapp/state/sync';
3
+ import { SQLiteStorage } from 'expo-sqlite/kv-store';
4
+
5
+ declare class ObservablePersistSqlite implements ObservablePersistPlugin {
6
+ private data;
7
+ private storage;
8
+ constructor(storage: SQLiteStorage);
9
+ getTable(table: string, init: any): any;
10
+ getMetadata(table: string): PersistMetadata;
11
+ set(table: string, changes: Change[]): void;
12
+ setMetadata(table: string, metadata: PersistMetadata): void;
13
+ deleteTable(table: string): undefined;
14
+ deleteMetadata(table: string): void;
15
+ private save;
16
+ }
17
+ declare function observablePersistSqlite(storage: SQLiteStorage): ObservablePersistSqlite;
18
+
19
+ export { ObservablePersistSqlite, observablePersistSqlite };
@@ -0,0 +1,72 @@
1
+ 'use strict';
2
+
3
+ var state = require('@legendapp/state');
4
+
5
+ // src/persist-plugins/expo-sqlite.ts
6
+ var { safeParse, safeStringify } = state.internal;
7
+ var MetadataSuffix = "__m";
8
+ var ObservablePersistSqlite = class {
9
+ constructor(storage) {
10
+ this.data = {};
11
+ if (!storage) {
12
+ console.error(
13
+ "[legend-state] ObservablePersistSqlite failed to initialize. You need to pass the SQLiteStorage instance."
14
+ );
15
+ }
16
+ this.storage = storage;
17
+ }
18
+ getTable(table, init) {
19
+ if (!this.storage)
20
+ return void 0;
21
+ if (this.data[table] === void 0) {
22
+ try {
23
+ const value = this.storage.getItemSync(table);
24
+ this.data[table] = value ? safeParse(value) : init;
25
+ } catch (e) {
26
+ console.error("[legend-state] ObservablePersistSqlite failed to parse", table);
27
+ }
28
+ }
29
+ return this.data[table];
30
+ }
31
+ getMetadata(table) {
32
+ return this.getTable(table + MetadataSuffix, {});
33
+ }
34
+ set(table, changes) {
35
+ if (!this.data[table]) {
36
+ this.data[table] = {};
37
+ }
38
+ this.data[table] = state.applyChanges(this.data[table], changes);
39
+ this.save(table);
40
+ }
41
+ setMetadata(table, metadata) {
42
+ table = table + MetadataSuffix;
43
+ this.data[table] = metadata;
44
+ this.save(table);
45
+ }
46
+ deleteTable(table) {
47
+ if (!this.storage)
48
+ return void 0;
49
+ delete this.data[table];
50
+ this.storage.removeItemSync(table);
51
+ }
52
+ deleteMetadata(table) {
53
+ this.deleteTable(table + MetadataSuffix);
54
+ }
55
+ // Private
56
+ save(table) {
57
+ if (!this.storage)
58
+ return void 0;
59
+ const v = this.data[table];
60
+ if (v !== void 0 && v !== null) {
61
+ this.storage.setItemSync(table, safeStringify(v));
62
+ } else {
63
+ this.storage.removeItemSync(table);
64
+ }
65
+ }
66
+ };
67
+ function observablePersistSqlite(storage) {
68
+ return new ObservablePersistSqlite(storage);
69
+ }
70
+
71
+ exports.ObservablePersistSqlite = ObservablePersistSqlite;
72
+ exports.observablePersistSqlite = observablePersistSqlite;