@oscarpalmer/mora 0.28.0 → 0.30.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.
Files changed (42) hide show
  1. package/dist/batch.mjs +15 -6
  2. package/dist/constants.d.mts +0 -1
  3. package/dist/constants.mjs +4 -3
  4. package/dist/effect.d.mts +5 -8
  5. package/dist/effect.mjs +23 -19
  6. package/dist/helpers/is.d.mts +9 -9
  7. package/dist/helpers/is.mjs +6 -0
  8. package/dist/helpers/proxy.d.mts +5 -9
  9. package/dist/helpers/proxy.mjs +4 -4
  10. package/dist/helpers/value.d.mts +3 -3
  11. package/dist/helpers/value.mjs +21 -3
  12. package/dist/index.d.mts +7 -8
  13. package/dist/index.mjs +1 -1
  14. package/dist/models.d.mts +356 -18
  15. package/dist/mora.full.mjs +458 -409
  16. package/dist/subscription.d.mts +1 -9
  17. package/dist/subscription.mjs +14 -15
  18. package/dist/value/array.d.mts +5 -133
  19. package/dist/value/array.mjs +91 -137
  20. package/dist/value/computed.d.mts +4 -12
  21. package/dist/value/computed.mjs +54 -50
  22. package/dist/value/reactive.d.mts +3 -38
  23. package/dist/value/reactive.mjs +10 -49
  24. package/dist/value/signal.d.mts +5 -21
  25. package/dist/value/signal.mjs +27 -49
  26. package/dist/value/store.d.mts +9 -92
  27. package/dist/value/store.mjs +42 -49
  28. package/package.json +8 -8
  29. package/src/batch.ts +22 -9
  30. package/src/constants.ts +3 -4
  31. package/src/effect.ts +31 -26
  32. package/src/helpers/is.ts +11 -10
  33. package/src/helpers/proxy.ts +23 -18
  34. package/src/helpers/value.ts +38 -3
  35. package/src/index.ts +6 -7
  36. package/src/models.ts +431 -16
  37. package/src/subscription.ts +20 -20
  38. package/src/value/array.ts +183 -265
  39. package/src/value/computed.ts +80 -74
  40. package/src/value/reactive.ts +16 -64
  41. package/src/value/signal.ts +34 -71
  42. package/src/value/store.ts +84 -177
package/dist/models.d.mts CHANGED
@@ -1,32 +1,213 @@
1
- import { Effect } from "./effect.mjs";
2
- import { Subscription } from "./subscription.mjs";
3
- import { Computed } from "./value/computed.mjs";
4
- import { Signal } from "./value/signal.mjs";
1
+ import { PROPERTY_LENGTH } from "./constants.mjs";
5
2
  import { GenericCallback, Key } from "@oscarpalmer/atoms/models";
6
-
7
3
  //#region src/models.d.ts
8
4
  type Active = {
9
- computed?: Computed<unknown>;
10
- effect?: Effect;
5
+ computed?: ComputedEffect;
6
+ effect?: EffectState;
11
7
  };
12
8
  type Batch = {
13
9
  depth: number;
14
- handlers: Set<Effect | Subscription>;
10
+ flushing: boolean;
11
+ handlers: Set<EffectState | Subscription>;
15
12
  };
13
+ type Computed<Value> = Reactive<Value> & SimpleReactive<Value>;
16
14
  type ComputedEffect = {
17
15
  dirty: boolean;
18
- instance: Effect;
16
+ instance: EffectState;
19
17
  };
18
+ type Effect = {};
20
19
  type EffectState = {
21
20
  callback: GenericCallback;
22
21
  };
23
- type InternalComputed = {
24
- readonly effect: ComputedEffect;
25
- readonly state: ReactiveState<unknown, unknown>;
26
- };
27
- type InternalEffect = {
28
- state: EffectState;
22
+ type Reactive<Value> = {
23
+ /**
24
+ * JSON representation of the value
25
+ *
26
+ * @returns JSON value
27
+ */
28
+ toJSON(): Value;
29
+ /**
30
+ * String representation of the value
31
+ *
32
+ * @returns Value as string
33
+ */
34
+ toString(): string;
29
35
  };
36
+ type ReactiveArray<Item> = {
37
+ /**
38
+ * The length of the array
39
+ */
40
+ get length(): number;
41
+ /**
42
+ * Set the length of the array
43
+ */
44
+ set length(value: number);
45
+ /**
46
+ * Get the value at an index
47
+ *
48
+ * @param index Index of item to get _(if negative, starts from the end)_
49
+ * @returns Item at index, or `undefined` if it doesn't exist
50
+ */
51
+ at(index: number): Item | undefined;
52
+ /**
53
+ * Clear the array
54
+ */
55
+ clear(): void;
56
+ /**
57
+ * Create a computed, filtered array
58
+ *
59
+ * @param callback Callback to evaluate each item
60
+ * @returns Computed array of filtered items
61
+ */
62
+ filter(callback: (item: Item, index: number, array: Item[]) => boolean): Computed<Item[]>;
63
+ /**
64
+ * Get the array
65
+ *
66
+ * @returns Array of items
67
+ */
68
+ get(): Item[];
69
+ /**
70
+ * Get the value at an index
71
+ *
72
+ * @param index Index of item to get _(if negative, starts from the end)_
73
+ * @returns Item at index, or `undefined` if it doesn't exist
74
+ */
75
+ get(index: number): Item | undefined;
76
+ /**
77
+ * Get the length of the array
78
+ *
79
+ * @returns Length of the array
80
+ */
81
+ get(property: typeof PROPERTY_LENGTH): number;
82
+ /**
83
+ * Create a computed, mapped array
84
+ *
85
+ * @param callback Callback to transform each item
86
+ * @returns Computed array of mapped items
87
+ */
88
+ map<Mapped>(callback: (item: Item, index: number, array: Item[]) => Mapped): Computed<Mapped[]>;
89
+ /**
90
+ * Notify dependents of changes
91
+ *
92
+ * _This bypasses equality checks and will immediately notify dependents.
93
+ * Use this only if you're modifying nested data that would be ignored by equality checks._
94
+ */
95
+ notify(): void;
96
+ /**
97
+ * Get the array _(without reactivity)_
98
+ *
99
+ * @returns Array of items
100
+ */
101
+ peek(): Item[];
102
+ /**
103
+ * Get the value at an index _(without reactivity)_
104
+ *
105
+ * @param index Index of item to get _(if negative, starts from the end)_
106
+ * @returns Item at index, or `undefined` if it doesn't exist
107
+ */
108
+ peek(index: number): Item | undefined;
109
+ /**
110
+ * Get the length of the array _(without reactivity)_
111
+ *
112
+ * @returns Length of the array
113
+ */
114
+ peek(property: typeof PROPERTY_LENGTH): number;
115
+ /**
116
+ * Remove and return the last item of the array
117
+ *
118
+ * @returns Removed item, or `undefined` if the array is empty
119
+ */
120
+ pop(): Item | undefined;
121
+ /**
122
+ * Add items to the end of the array
123
+ *
124
+ * @param items Items to add
125
+ * @returns New array length
126
+ */
127
+ push(...items: Item[]): number;
128
+ /**
129
+ * Create a computed, filtered, and mapped array
130
+ *
131
+ * @param filter Callback to evaluate each item
132
+ * @param map Callback to transform each item
133
+ * @returns Computed array of mapped items
134
+ */
135
+ select<Mapped>(filter: (item: Item, index: number, array: Item[]) => boolean, map: (item: Item, index: number, array: Item[]) => Mapped): Computed<Mapped[]>;
136
+ /**
137
+ * Set the value
138
+ *
139
+ * @param value New array of items _(defaults to an empty array)_
140
+ */
141
+ set(value?: Item[] | (() => null | undefined | Item[] | Promise<null | undefined | Item[]>) | Promise<null | undefined | Item[]>): void;
142
+ /**
143
+ * Set the value at an index
144
+ *
145
+ * @param index Index of item to set _(if negative, starts from the end)_
146
+ * @param value New item
147
+ */
148
+ set(index: number, value: Item | (() => Item | Promise<Item>) | Promise<Item>): void;
149
+ /**
150
+ * Set the length of the array
151
+ *
152
+ * @param value New array length
153
+ */
154
+ set(property: typeof PROPERTY_LENGTH, value: number): void;
155
+ /**
156
+ * Remove and return the first item of the array
157
+ *
158
+ * @returns Removed item, or `undefined` if the array is empty
159
+ */
160
+ shift(): Item | undefined;
161
+ /**
162
+ * Remove and return items from the array _(and optionally add new items)_
163
+ *
164
+ * @param from Index to start removing items from
165
+ * @param to Index to stop removing items at _(defaults to the end of the array)_
166
+ * @param items Optional items to add
167
+ * @returns Removed items
168
+ */
169
+ splice(from: number, to?: number, ...items: Item[]): Item[];
170
+ /**
171
+ * Subscribe to changes
172
+ *
173
+ * @param callback Callback for changes
174
+ * @returns Unsubscribe callback
175
+ */
176
+ subscribe(callback: (value: Item[]) => void): Unsubscribe;
177
+ /**
178
+ * Subscribe to changes at a specific index
179
+ *
180
+ * @param index Index of item to subscribe to
181
+ * @param callback Callback for changes
182
+ * @returns Unsubscribe callback
183
+ */
184
+ subscribe(index: number, callback: (value: Item | undefined) => void): Unsubscribe;
185
+ /**
186
+ * Add items to the beginning of the array
187
+ * @param items Items to add
188
+ * @returns New array length
189
+ */
190
+ unshift(...items: Item[]): number;
191
+ /**
192
+ * Unsubscribe from changes for a specific index
193
+ *
194
+ * @param index Index of the value to unsubscribe from
195
+ * @param callback Callback to unsubscribe
196
+ */
197
+ unsubscribe(index: number, callback: (item: Item | undefined) => void): void;
198
+ /**
199
+ * Unsubscribe from changes
200
+ *
201
+ * @param callback Callback to unsubscribe
202
+ */
203
+ unsubscribe(callback: (array: Item[]) => void): void;
204
+ /**
205
+ * Update the value _(based on the current value)_
206
+ *
207
+ * @param callback Callback to update the value
208
+ */
209
+ update(callback: (value: Item[]) => Item[]): void;
210
+ } & Reactive<Item[]>;
30
211
  type ReactiveOptions<Value> = {
31
212
  /**
32
213
  * Method for comparing values for equality
@@ -38,14 +219,125 @@ type ReactiveOptions<Value> = {
38
219
  equal?: (first: Value, second: Value) => boolean;
39
220
  };
40
221
  type ReactiveState<Value, Equal> = {
41
- computeds: Set<Computed<unknown>>;
42
- effects: Set<Effect>;
222
+ computeds: Set<ComputedEffect>;
223
+ effects: Set<EffectState>;
43
224
  equal: (first: Equal, second: Equal) => boolean;
44
225
  promise?: Promise<Value>;
45
226
  promises?: Map<Key, Promise<never>>;
46
227
  subscriptions: Map<GenericCallback, Subscription>;
47
228
  value: Value;
48
229
  };
230
+ type ReactiveStore<Value> = {
231
+ /**
232
+ * Get the value
233
+ *
234
+ * @returns Current value
235
+ */
236
+ get(): Value;
237
+ /**
238
+ * Get a value by key
239
+ *
240
+ * @param key Key of the value to get
241
+ * @returns Value for the specified key, or `undefined` if it doesn't exist
242
+ */
243
+ get<Key extends keyof Value>(key: Key): Value[Key];
244
+ /**
245
+ * Get a value by key
246
+ *
247
+ * @param key Key of the value to get
248
+ * @returns Value for the specified key, or `undefined` if it doesn't exist
249
+ */
250
+ get(key: Key): unknown;
251
+ /**
252
+ * Notify dependents of changes
253
+ *
254
+ * _This bypasses equality checks and will immediately notify dependents.
255
+ * Use this only if you're modifying nested data that would be ignored by equality checks._
256
+ */
257
+ notify(): void;
258
+ /**
259
+ * Get the value _(without reactivity)_
260
+ *
261
+ * @returns Current value
262
+ */
263
+ peek(): Value;
264
+ /**
265
+ * Get a value by key _(without reactivity)_
266
+ *
267
+ * @param key Key of the value to get
268
+ * @returns Value for the specified key, or `undefined` if it doesn't exist
269
+ */
270
+ peek<Key extends keyof Value>(key: Key): Value[Key];
271
+ /**
272
+ * Get a value by key _(without reactivity)_
273
+ *
274
+ * @param key Key of the value to get
275
+ * @returns Value for the specified key, or `undefined` if it doesn't exist
276
+ */
277
+ peek(key: Key): unknown;
278
+ /**
279
+ * Set the value
280
+ *
281
+ * @param value New value _(defaults to an empty object)_
282
+ */
283
+ set(value?: Value | (() => null | undefined | Value | Promise<null | undefined | Value>) | Promise<null | undefined | Value>): void;
284
+ /**
285
+ * Set a value by key
286
+ *
287
+ * @param key Key of the value to set
288
+ * @param value New value
289
+ */
290
+ set<Key extends keyof Value>(key: Key, value: Value[Key] | (() => Value[Key] | Promise<Value[Key]>) | Promise<Value[Key]>): void;
291
+ /**
292
+ * Set a value by key
293
+ *
294
+ * @param key Key of the value to set
295
+ * @param value New value
296
+ */
297
+ set(key: Key, value: unknown): void;
298
+ /**
299
+ * Subscribe to changes
300
+ *
301
+ * @param callback Callback for changes
302
+ * @returns Unsubscribe callback
303
+ */
304
+ subscribe(callback: (value: Value) => void): Unsubscribe;
305
+ /**
306
+ * Subscribe to changes for a specific key
307
+ *
308
+ * @param key Key of the value to subscribe to
309
+ * @param callback Callback for changes
310
+ * @returns Unsubscribe callback
311
+ */
312
+ subscribe<Key extends keyof Value>(key: Key, callback: (value: Value[Key] | undefined) => void): Unsubscribe;
313
+ /**
314
+ * Subscribe to changes for a specific key
315
+ *
316
+ * @param key Key of the value to subscribe to
317
+ * @param callback Callback for changes
318
+ * @returns Unsubscribe callback
319
+ */
320
+ subscribe(key: Key, callback: (value: unknown) => void): Unsubscribe;
321
+ /**
322
+ * Unsubscribe from changes for a specific key
323
+ *
324
+ * @param key Key of the value to unsubscribe from
325
+ * @param callback Callback to unsubscribe
326
+ */
327
+ unsubscribe<Key extends keyof Value>(key: Key, callback: (value: Value[Key] | undefined) => void): void;
328
+ /**
329
+ * Unsubscribe from changes
330
+ *
331
+ * @param callback Callback to unsubscribe
332
+ */
333
+ unsubscribe(callback: (value: Value) => void): void;
334
+ /**
335
+ * Update the value _(based on the current value)_
336
+ *
337
+ * @param callback Callback to update the value
338
+ */
339
+ update(callback: (value: Value) => Value): void;
340
+ } & Reactive<Value>;
49
341
  type SetValueInProxyParameters<Value, Equal> = {
50
342
  target: Value;
51
343
  property: PropertyKey;
@@ -54,9 +346,55 @@ type SetValueInProxyParameters<Value, Equal> = {
54
346
  isArray: boolean;
55
347
  length?: Signal<number>;
56
348
  };
349
+ type Signal<Value> = {
350
+ /**
351
+ * Set the value
352
+ *
353
+ * @param value New value
354
+ */
355
+ set(value: Value | (() => Value | Promise<Value>) | Promise<Value>): void;
356
+ /**
357
+ * Update the value _(based on the current value)_
358
+ *
359
+ * @param callback Callback to update the value
360
+ */
361
+ update(callback: (value: Value) => Value): void;
362
+ } & Reactive<Value> & SimpleReactive<Value>;
363
+ type SimpleReactive<Value> = {
364
+ /**
365
+ * Get the value
366
+ *
367
+ * @returns Current value
368
+ */
369
+ get(): Value;
370
+ /**
371
+ * Get the value _(without reactivity)_
372
+ *
373
+ * @returns Current value
374
+ */
375
+ peek(): Value;
376
+ /**
377
+ * Subscribe to changes
378
+ *
379
+ * @param callback Callback for changes
380
+ * @returns Unsubscribe callback
381
+ */
382
+ subscribe(callback: (value: Value) => void): Unsubscribe;
383
+ /**
384
+ * Unsubscribe from changes
385
+ *
386
+ * @param callback Callback to unsubscribe
387
+ */
388
+ unsubscribe(callback: (value: Value) => void): void;
389
+ };
390
+ type Subscription = {
391
+ callback: GenericCallback;
392
+ state: ReactiveState<unknown, never>;
393
+ destroy(): void;
394
+ };
57
395
  /**
58
396
  * Unsubscribe from changes
59
397
  */
60
398
  type Unsubscribe = () => void;
61
399
  //#endregion
62
- export { Active, Batch, ComputedEffect, EffectState, InternalComputed, InternalEffect, ReactiveOptions, ReactiveState, SetValueInProxyParameters, Unsubscribe };
400
+ export { Active, Batch, Computed, ComputedEffect, Effect, EffectState, Reactive, ReactiveArray, ReactiveOptions, ReactiveState, ReactiveStore, SetValueInProxyParameters, Signal, Subscription, Unsubscribe };