@choksheak/react-utils 0.1.6 → 0.1.7

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 (58) hide show
  1. package/docs/assets/navigation.js +1 -1
  2. package/docs/assets/search.js +1 -1
  3. package/docs/classes/sharedQuery.SharedQuery.html +15 -0
  4. package/docs/classes/sharedState.SharedState.html +8 -0
  5. package/docs/classes/sharedState.SharedStateConfig.html +5 -5
  6. package/docs/classes/utils_storage.InMemoryStorageAdapter.html +9 -0
  7. package/docs/classes/utils_storage.IndexedDbAdapter.html +9 -0
  8. package/docs/classes/utils_storage.LocalStorageAdapter.html +9 -0
  9. package/docs/functions/sharedQuery.sharedQuery.html +5 -0
  10. package/docs/functions/sharedQuery.useQuery.html +4 -0
  11. package/docs/functions/sharedState.sharedState.html +2 -2
  12. package/docs/functions/sharedState.useSharedState.html +2 -2
  13. package/docs/functions/sharedState.useSharedStateSetter.html +2 -2
  14. package/docs/functions/sharedState.useSharedStateValue.html +2 -2
  15. package/docs/functions/utils_storage.getStorageAdapter.html +1 -0
  16. package/docs/functions/utils_stringify.stringifyDeterministicForKeys.html +7 -0
  17. package/docs/modules/sharedQuery.html +1 -0
  18. package/docs/modules/sharedState.html +1 -1
  19. package/docs/modules/utils_storage.html +1 -0
  20. package/docs/modules/utils_stringify.html +1 -0
  21. package/docs/modules.html +1 -1
  22. package/docs/types/sharedQuery.FetchFn.html +1 -0
  23. package/docs/types/sharedQuery.FetchedData.html +3 -0
  24. package/docs/types/sharedQuery.QueryStateValue.html +4 -0
  25. package/docs/types/sharedQuery.SharedQueryOptions.html +1 -0
  26. package/docs/types/sharedQuery.SharedQueryState.html +3 -0
  27. package/docs/types/sharedState.SharedStateOptions.html +1 -0
  28. package/docs/types/utils_storage.StorageAdapter.html +5 -0
  29. package/docs/types/utils_storage.StorageOptions.html +5 -0
  30. package/docs/variables/fetcher.fetcher.html +1 -1
  31. package/docs/variables/fetcher.fetcherWithRetries.html +1 -1
  32. package/package.json +9 -6
  33. package/sharedQuery.d.mts +61 -0
  34. package/sharedQuery.d.ts +58 -0
  35. package/sharedQuery.js +471 -0
  36. package/sharedQuery.mjs +444 -0
  37. package/sharedState.d.mts +21 -16
  38. package/sharedState.d.ts +19 -15
  39. package/sharedState.js +156 -85
  40. package/sharedState.mjs +155 -85
  41. package/src/sharedQuery.ts +303 -0
  42. package/src/sharedState.ts +74 -137
  43. package/src/utils/storage.ts +197 -0
  44. package/src/utils/stringify.test.ts +38 -0
  45. package/src/utils/stringify.ts +49 -0
  46. package/utils/storage.d.mts +46 -0
  47. package/utils/storage.d.ts +44 -0
  48. package/utils/storage.js +162 -0
  49. package/utils/storage.mjs +134 -0
  50. package/utils/stringify.d.mts +12 -0
  51. package/utils/stringify.d.ts +10 -0
  52. package/utils/stringify.js +58 -0
  53. package/utils/stringify.mjs +33 -0
  54. package/utils/stringify.test.d.mts +2 -0
  55. package/utils/stringify.test.d.ts +2 -0
  56. package/utils/stringify.test.js +64 -0
  57. package/utils/stringify.test.mjs +81 -0
  58. package/docs/types/sharedState.SharedState.html +0 -6
package/sharedState.js CHANGED
@@ -20,6 +20,7 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
20
20
  // src/sharedState.ts
21
21
  var sharedState_exports = {};
22
22
  __export(sharedState_exports, {
23
+ SharedState: () => SharedState,
23
24
  SharedStateConfig: () => SharedStateConfig,
24
25
  sharedState: () => sharedState,
25
26
  useSharedState: () => useSharedState,
@@ -27,17 +28,119 @@ __export(sharedState_exports, {
27
28
  useSharedStateValue: () => useSharedStateValue
28
29
  });
29
30
  module.exports = __toCommonJS(sharedState_exports);
30
- var import_kvStore = require("@choksheak/ts-utils/kvStore");
31
+ var import_kvStore2 = require("@choksheak/ts-utils/kvStore");
31
32
  var import_timeConstants = require("@choksheak/ts-utils/timeConstants");
32
33
  var import_react = require("react");
34
+
35
+ // src/utils/storage.ts
36
+ var import_kvStore = require("@choksheak/ts-utils/kvStore");
37
+ function getStorageAdapter(options, defaultStoreExpiryMs) {
38
+ const { localStorageKey, indexedDbKey, storeExpiryMs, store } = options ?? {};
39
+ if (store) {
40
+ return store;
41
+ }
42
+ const expiryMs = storeExpiryMs || defaultStoreExpiryMs;
43
+ if (localStorageKey) {
44
+ return new LocalStorageAdapter(localStorageKey, expiryMs);
45
+ }
46
+ if (indexedDbKey) {
47
+ return new IndexedDbAdapter(indexedDbKey, expiryMs);
48
+ }
49
+ return null;
50
+ }
51
+ var LocalStorageAdapter = class {
52
+ constructor(keyPrefix, expiryMs) {
53
+ this.keyPrefix = keyPrefix;
54
+ this.expiryMs = expiryMs;
55
+ }
56
+ save(key, value) {
57
+ if (typeof window === "undefined") return;
58
+ const fullKey = this.keyPrefix + ":" + key;
59
+ window.localStorage.setItem(
60
+ fullKey,
61
+ JSON.stringify({
62
+ value,
63
+ expiresAt: this.expiryMs ? Date.now() + this.expiryMs : 0
64
+ })
65
+ );
66
+ }
67
+ load(key) {
68
+ if (typeof window === "undefined") return void 0;
69
+ const fullKey = this.keyPrefix + ":" + key;
70
+ const raw = window.localStorage.getItem(fullKey);
71
+ if (!raw) return void 0;
72
+ try {
73
+ const box = JSON.parse(raw);
74
+ if (!box || box.expiresAt && Date.now() >= box.expiresAt) {
75
+ window.localStorage.removeItem(fullKey);
76
+ return void 0;
77
+ }
78
+ return box.value;
79
+ } catch {
80
+ window.localStorage.removeItem(fullKey);
81
+ return void 0;
82
+ }
83
+ }
84
+ delete(key) {
85
+ if (typeof window === "undefined") return;
86
+ const fullKey = this.keyPrefix + ":" + key;
87
+ window.localStorage.removeItem(fullKey);
88
+ }
89
+ clear() {
90
+ if (typeof window === "undefined") return;
91
+ for (const key of Object.keys(window.localStorage)) {
92
+ if (key.startsWith(this.keyPrefix)) {
93
+ window.localStorage.removeItem(key);
94
+ }
95
+ }
96
+ }
97
+ };
98
+ var IndexedDbAdapter = class {
99
+ constructor(keyPrefix, expiryMs) {
100
+ this.keyPrefix = keyPrefix;
101
+ this.expiryMs = expiryMs;
102
+ }
103
+ async save(key, value) {
104
+ if (typeof window === "undefined") return;
105
+ const fullKey = this.keyPrefix + ":" + key;
106
+ await import_kvStore.kvStore.set(fullKey, JSON.stringify(value), this.expiryMs);
107
+ }
108
+ async load(key) {
109
+ if (typeof window === "undefined") return void 0;
110
+ const fullKey = this.keyPrefix + ":" + key;
111
+ const raw = await import_kvStore.kvStore.get(fullKey);
112
+ if (raw === void 0) return void 0;
113
+ try {
114
+ return JSON.parse(raw);
115
+ } catch {
116
+ await import_kvStore.kvStore.delete(fullKey);
117
+ return void 0;
118
+ }
119
+ }
120
+ async delete(key) {
121
+ if (typeof window === "undefined") return;
122
+ const fullKey = this.keyPrefix + ":" + key;
123
+ await import_kvStore.kvStore.delete(fullKey);
124
+ }
125
+ async clear() {
126
+ if (typeof window === "undefined") return;
127
+ await import_kvStore.kvStore.forEach(async (k) => {
128
+ if (k.startsWith(this.keyPrefix)) {
129
+ await import_kvStore.kvStore.delete(k);
130
+ }
131
+ });
132
+ }
133
+ };
134
+
135
+ // src/sharedState.ts
33
136
  var SharedStateConfig = class {
34
137
  /**
35
- * Default duration for persistence expiration in milliseconds. Initial value
138
+ * Default duration for storage expiration in milliseconds. Initial value
36
139
  * is 30 days, but can be changed to anything.
37
140
  */
38
- static persistExpiryMs = import_timeConstants.MS_PER_DAY * 30;
141
+ static storeExpiryMs = import_timeConstants.MS_PER_DAY * 30;
39
142
  /**
40
- * True to load from persistence only on mount, false (default) to load in
143
+ * True to load from storage only on mount, false (default) to load in
41
144
  * the top level scope when the shared state is defined.
42
145
  */
43
146
  static lazyLoad = false;
@@ -56,6 +159,9 @@ var PubSubStore = class {
56
159
  this.dataByKey.set(key, value);
57
160
  this.notify(key, value, prev);
58
161
  }
162
+ delete(key) {
163
+ this.dataByKey.delete(key);
164
+ }
59
165
  setNoNotify(key, value) {
60
166
  this.dataByKey.set(key, value);
61
167
  }
@@ -85,51 +191,58 @@ var PubSubStore = class {
85
191
  }
86
192
  }
87
193
  };
88
- var store = new PubSubStore();
194
+ var pubSubStore = new PubSubStore();
195
+ var STORAGE_KEY = "state";
89
196
  var stateKey = 0;
90
- function sharedState(defaultValue, options) {
91
- const { localStorageKey, indexedDbKey, persistExpiryMs, lazyLoad } = options ?? {};
92
- const key = String(stateKey++);
93
- let persistenceAdapter;
94
- const expiryMs = persistExpiryMs ?? SharedStateConfig.persistExpiryMs;
95
- if (localStorageKey) {
96
- persistenceAdapter = new LocalStorageAdapter(localStorageKey, expiryMs);
97
- } else if (indexedDbKey) {
98
- persistenceAdapter = new IndexedDbAdapter(indexedDbKey, expiryMs);
197
+ var SharedState = class {
198
+ constructor(defaultValue, options) {
199
+ this.defaultValue = defaultValue;
200
+ this.pubSubKey = String(stateKey++);
201
+ this.storageAdapter = getStorageAdapter(options, import_kvStore2.DEFAULT_EXPIRY_DELTA_MS);
202
+ pubSubStore.setNoNotify(this.pubSubKey, defaultValue);
203
+ const lazyLoad = options?.lazyLoad;
204
+ const lazy = lazyLoad !== void 0 ? lazyLoad : SharedStateConfig.lazyLoad;
205
+ if (!lazy) {
206
+ void this.initDefaultValueOnce();
207
+ }
99
208
  }
100
- function subscribe(subscriber) {
101
- return store.subscribe(key, () => subscriber());
209
+ pubSubKey;
210
+ storageAdapter;
211
+ initDone = false;
212
+ // `subscribe` function required by useSyncExternalStore
213
+ subscribe(subscriber) {
214
+ return pubSubStore.subscribe(this.pubSubKey, () => subscriber());
102
215
  }
103
- function getSnapshot() {
104
- return store.get(key);
216
+ // Get the value of the shared state.
217
+ // `getSnapshot` function — must return same ref if value unchanged
218
+ getSnapshot() {
219
+ return pubSubStore.get(this.pubSubKey);
105
220
  }
106
- function setValue(next) {
221
+ // Set the value of the shared state.
222
+ setValue(next) {
107
223
  if (typeof next === "function") {
108
- const prev = store.get(key);
224
+ const prev = pubSubStore.get(this.pubSubKey);
109
225
  next = next(prev);
110
226
  }
111
- store.set(key, next);
112
- void persistenceAdapter?.save?.(next);
113
- }
114
- store.setNoNotify(key, defaultValue);
115
- const state = {
116
- subscribe,
117
- getSnapshot,
118
- // initial default handling
119
- initDefaultValueOnce: async () => {
120
- if (state.initDone) return;
121
- state.initDone = true;
122
- const v = await persistenceAdapter?.load?.();
123
- store.set(key, v !== void 0 ? v : defaultValue);
124
- },
125
- initDone: false,
126
- setValue
127
- };
128
- const lazy = lazyLoad !== void 0 ? lazyLoad : SharedStateConfig.lazyLoad;
129
- if (!lazy) {
130
- void state.initDefaultValueOnce();
131
- }
132
- return state;
227
+ pubSubStore.set(this.pubSubKey, next);
228
+ void this.storageAdapter?.save(STORAGE_KEY, next);
229
+ }
230
+ // Remove the value of the shared state. Actually this just sets the value
231
+ // back to the given default value.
232
+ delete() {
233
+ pubSubStore.set(this.pubSubKey, this.defaultValue);
234
+ void this.storageAdapter?.save(STORAGE_KEY, this.defaultValue);
235
+ }
236
+ // Initial default handling
237
+ async initDefaultValueOnce() {
238
+ if (this.initDone) return;
239
+ this.initDone = true;
240
+ const v = await this.storageAdapter?.load(STORAGE_KEY);
241
+ pubSubStore.set(this.pubSubKey, v !== void 0 ? v : this.defaultValue);
242
+ }
243
+ };
244
+ function sharedState(defaultValue, options) {
245
+ return new SharedState(defaultValue, options);
133
246
  }
134
247
  function useSharedState(state) {
135
248
  state.initDefaultValueOnce();
@@ -147,51 +260,9 @@ function useSharedStateValue(state) {
147
260
  function useSharedStateSetter(state) {
148
261
  return useSharedState(state)[1];
149
262
  }
150
- var LocalStorageAdapter = class {
151
- constructor(key, expiryMs) {
152
- this.key = key;
153
- this.expiryMs = expiryMs;
154
- }
155
- save(value) {
156
- if (typeof window === "undefined") return;
157
- window.localStorage.setItem(
158
- this.key,
159
- JSON.stringify({
160
- value,
161
- expiresAt: Date.now() + this.expiryMs
162
- })
163
- );
164
- }
165
- load() {
166
- if (typeof window === "undefined") return void 0;
167
- const raw = window.localStorage.getItem(this.key);
168
- if (!raw) return void 0;
169
- const box = JSON.parse(raw);
170
- if (!box || !box?.expiresAt || Date.now() >= box.expiresAt) {
171
- window.localStorage.removeItem(this.key);
172
- return void 0;
173
- }
174
- return box.value;
175
- }
176
- };
177
- var IndexedDbAdapter = class {
178
- constructor(key, expiryMs) {
179
- this.key = key;
180
- this.expiryMs = expiryMs;
181
- }
182
- async save(value) {
183
- if (typeof window === "undefined") return;
184
- await import_kvStore.kvStore.set(this.key, JSON.stringify(value), this.expiryMs);
185
- }
186
- async load() {
187
- if (typeof window === "undefined") return void 0;
188
- const raw = await import_kvStore.kvStore.get(this.key);
189
- if (raw === void 0) return void 0;
190
- return JSON.parse(raw);
191
- }
192
- };
193
263
  // Annotate the CommonJS export names for ESM import in node:
194
264
  0 && (module.exports = {
265
+ SharedState,
195
266
  SharedStateConfig,
196
267
  sharedState,
197
268
  useSharedState,
package/sharedState.mjs CHANGED
@@ -1,15 +1,117 @@
1
1
  // src/sharedState.ts
2
- import { kvStore } from "@choksheak/ts-utils/kvStore";
2
+ import { DEFAULT_EXPIRY_DELTA_MS } from "@choksheak/ts-utils/kvStore";
3
3
  import { MS_PER_DAY } from "@choksheak/ts-utils/timeConstants";
4
4
  import { useSyncExternalStore } from "react";
5
+
6
+ // src/utils/storage.ts
7
+ import { kvStore } from "@choksheak/ts-utils/kvStore";
8
+ function getStorageAdapter(options, defaultStoreExpiryMs) {
9
+ const { localStorageKey, indexedDbKey, storeExpiryMs, store } = options ?? {};
10
+ if (store) {
11
+ return store;
12
+ }
13
+ const expiryMs = storeExpiryMs || defaultStoreExpiryMs;
14
+ if (localStorageKey) {
15
+ return new LocalStorageAdapter(localStorageKey, expiryMs);
16
+ }
17
+ if (indexedDbKey) {
18
+ return new IndexedDbAdapter(indexedDbKey, expiryMs);
19
+ }
20
+ return null;
21
+ }
22
+ var LocalStorageAdapter = class {
23
+ constructor(keyPrefix, expiryMs) {
24
+ this.keyPrefix = keyPrefix;
25
+ this.expiryMs = expiryMs;
26
+ }
27
+ save(key, value) {
28
+ if (typeof window === "undefined") return;
29
+ const fullKey = this.keyPrefix + ":" + key;
30
+ window.localStorage.setItem(
31
+ fullKey,
32
+ JSON.stringify({
33
+ value,
34
+ expiresAt: this.expiryMs ? Date.now() + this.expiryMs : 0
35
+ })
36
+ );
37
+ }
38
+ load(key) {
39
+ if (typeof window === "undefined") return void 0;
40
+ const fullKey = this.keyPrefix + ":" + key;
41
+ const raw = window.localStorage.getItem(fullKey);
42
+ if (!raw) return void 0;
43
+ try {
44
+ const box = JSON.parse(raw);
45
+ if (!box || box.expiresAt && Date.now() >= box.expiresAt) {
46
+ window.localStorage.removeItem(fullKey);
47
+ return void 0;
48
+ }
49
+ return box.value;
50
+ } catch {
51
+ window.localStorage.removeItem(fullKey);
52
+ return void 0;
53
+ }
54
+ }
55
+ delete(key) {
56
+ if (typeof window === "undefined") return;
57
+ const fullKey = this.keyPrefix + ":" + key;
58
+ window.localStorage.removeItem(fullKey);
59
+ }
60
+ clear() {
61
+ if (typeof window === "undefined") return;
62
+ for (const key of Object.keys(window.localStorage)) {
63
+ if (key.startsWith(this.keyPrefix)) {
64
+ window.localStorage.removeItem(key);
65
+ }
66
+ }
67
+ }
68
+ };
69
+ var IndexedDbAdapter = class {
70
+ constructor(keyPrefix, expiryMs) {
71
+ this.keyPrefix = keyPrefix;
72
+ this.expiryMs = expiryMs;
73
+ }
74
+ async save(key, value) {
75
+ if (typeof window === "undefined") return;
76
+ const fullKey = this.keyPrefix + ":" + key;
77
+ await kvStore.set(fullKey, JSON.stringify(value), this.expiryMs);
78
+ }
79
+ async load(key) {
80
+ if (typeof window === "undefined") return void 0;
81
+ const fullKey = this.keyPrefix + ":" + key;
82
+ const raw = await kvStore.get(fullKey);
83
+ if (raw === void 0) return void 0;
84
+ try {
85
+ return JSON.parse(raw);
86
+ } catch {
87
+ await kvStore.delete(fullKey);
88
+ return void 0;
89
+ }
90
+ }
91
+ async delete(key) {
92
+ if (typeof window === "undefined") return;
93
+ const fullKey = this.keyPrefix + ":" + key;
94
+ await kvStore.delete(fullKey);
95
+ }
96
+ async clear() {
97
+ if (typeof window === "undefined") return;
98
+ await kvStore.forEach(async (k) => {
99
+ if (k.startsWith(this.keyPrefix)) {
100
+ await kvStore.delete(k);
101
+ }
102
+ });
103
+ }
104
+ };
105
+
106
+ // src/sharedState.ts
5
107
  var SharedStateConfig = class {
6
108
  /**
7
- * Default duration for persistence expiration in milliseconds. Initial value
109
+ * Default duration for storage expiration in milliseconds. Initial value
8
110
  * is 30 days, but can be changed to anything.
9
111
  */
10
- static persistExpiryMs = MS_PER_DAY * 30;
112
+ static storeExpiryMs = MS_PER_DAY * 30;
11
113
  /**
12
- * True to load from persistence only on mount, false (default) to load in
114
+ * True to load from storage only on mount, false (default) to load in
13
115
  * the top level scope when the shared state is defined.
14
116
  */
15
117
  static lazyLoad = false;
@@ -28,6 +130,9 @@ var PubSubStore = class {
28
130
  this.dataByKey.set(key, value);
29
131
  this.notify(key, value, prev);
30
132
  }
133
+ delete(key) {
134
+ this.dataByKey.delete(key);
135
+ }
31
136
  setNoNotify(key, value) {
32
137
  this.dataByKey.set(key, value);
33
138
  }
@@ -57,51 +162,58 @@ var PubSubStore = class {
57
162
  }
58
163
  }
59
164
  };
60
- var store = new PubSubStore();
165
+ var pubSubStore = new PubSubStore();
166
+ var STORAGE_KEY = "state";
61
167
  var stateKey = 0;
62
- function sharedState(defaultValue, options) {
63
- const { localStorageKey, indexedDbKey, persistExpiryMs, lazyLoad } = options ?? {};
64
- const key = String(stateKey++);
65
- let persistenceAdapter;
66
- const expiryMs = persistExpiryMs ?? SharedStateConfig.persistExpiryMs;
67
- if (localStorageKey) {
68
- persistenceAdapter = new LocalStorageAdapter(localStorageKey, expiryMs);
69
- } else if (indexedDbKey) {
70
- persistenceAdapter = new IndexedDbAdapter(indexedDbKey, expiryMs);
168
+ var SharedState = class {
169
+ constructor(defaultValue, options) {
170
+ this.defaultValue = defaultValue;
171
+ this.pubSubKey = String(stateKey++);
172
+ this.storageAdapter = getStorageAdapter(options, DEFAULT_EXPIRY_DELTA_MS);
173
+ pubSubStore.setNoNotify(this.pubSubKey, defaultValue);
174
+ const lazyLoad = options?.lazyLoad;
175
+ const lazy = lazyLoad !== void 0 ? lazyLoad : SharedStateConfig.lazyLoad;
176
+ if (!lazy) {
177
+ void this.initDefaultValueOnce();
178
+ }
71
179
  }
72
- function subscribe(subscriber) {
73
- return store.subscribe(key, () => subscriber());
180
+ pubSubKey;
181
+ storageAdapter;
182
+ initDone = false;
183
+ // `subscribe` function required by useSyncExternalStore
184
+ subscribe(subscriber) {
185
+ return pubSubStore.subscribe(this.pubSubKey, () => subscriber());
74
186
  }
75
- function getSnapshot() {
76
- return store.get(key);
187
+ // Get the value of the shared state.
188
+ // `getSnapshot` function — must return same ref if value unchanged
189
+ getSnapshot() {
190
+ return pubSubStore.get(this.pubSubKey);
77
191
  }
78
- function setValue(next) {
192
+ // Set the value of the shared state.
193
+ setValue(next) {
79
194
  if (typeof next === "function") {
80
- const prev = store.get(key);
195
+ const prev = pubSubStore.get(this.pubSubKey);
81
196
  next = next(prev);
82
197
  }
83
- store.set(key, next);
84
- void persistenceAdapter?.save?.(next);
85
- }
86
- store.setNoNotify(key, defaultValue);
87
- const state = {
88
- subscribe,
89
- getSnapshot,
90
- // initial default handling
91
- initDefaultValueOnce: async () => {
92
- if (state.initDone) return;
93
- state.initDone = true;
94
- const v = await persistenceAdapter?.load?.();
95
- store.set(key, v !== void 0 ? v : defaultValue);
96
- },
97
- initDone: false,
98
- setValue
99
- };
100
- const lazy = lazyLoad !== void 0 ? lazyLoad : SharedStateConfig.lazyLoad;
101
- if (!lazy) {
102
- void state.initDefaultValueOnce();
103
- }
104
- return state;
198
+ pubSubStore.set(this.pubSubKey, next);
199
+ void this.storageAdapter?.save(STORAGE_KEY, next);
200
+ }
201
+ // Remove the value of the shared state. Actually this just sets the value
202
+ // back to the given default value.
203
+ delete() {
204
+ pubSubStore.set(this.pubSubKey, this.defaultValue);
205
+ void this.storageAdapter?.save(STORAGE_KEY, this.defaultValue);
206
+ }
207
+ // Initial default handling
208
+ async initDefaultValueOnce() {
209
+ if (this.initDone) return;
210
+ this.initDone = true;
211
+ const v = await this.storageAdapter?.load(STORAGE_KEY);
212
+ pubSubStore.set(this.pubSubKey, v !== void 0 ? v : this.defaultValue);
213
+ }
214
+ };
215
+ function sharedState(defaultValue, options) {
216
+ return new SharedState(defaultValue, options);
105
217
  }
106
218
  function useSharedState(state) {
107
219
  state.initDefaultValueOnce();
@@ -119,50 +231,8 @@ function useSharedStateValue(state) {
119
231
  function useSharedStateSetter(state) {
120
232
  return useSharedState(state)[1];
121
233
  }
122
- var LocalStorageAdapter = class {
123
- constructor(key, expiryMs) {
124
- this.key = key;
125
- this.expiryMs = expiryMs;
126
- }
127
- save(value) {
128
- if (typeof window === "undefined") return;
129
- window.localStorage.setItem(
130
- this.key,
131
- JSON.stringify({
132
- value,
133
- expiresAt: Date.now() + this.expiryMs
134
- })
135
- );
136
- }
137
- load() {
138
- if (typeof window === "undefined") return void 0;
139
- const raw = window.localStorage.getItem(this.key);
140
- if (!raw) return void 0;
141
- const box = JSON.parse(raw);
142
- if (!box || !box?.expiresAt || Date.now() >= box.expiresAt) {
143
- window.localStorage.removeItem(this.key);
144
- return void 0;
145
- }
146
- return box.value;
147
- }
148
- };
149
- var IndexedDbAdapter = class {
150
- constructor(key, expiryMs) {
151
- this.key = key;
152
- this.expiryMs = expiryMs;
153
- }
154
- async save(value) {
155
- if (typeof window === "undefined") return;
156
- await kvStore.set(this.key, JSON.stringify(value), this.expiryMs);
157
- }
158
- async load() {
159
- if (typeof window === "undefined") return void 0;
160
- const raw = await kvStore.get(this.key);
161
- if (raw === void 0) return void 0;
162
- return JSON.parse(raw);
163
- }
164
- };
165
234
  export {
235
+ SharedState,
166
236
  SharedStateConfig,
167
237
  sharedState,
168
238
  useSharedState,