@ersbeth/picoflow 1.0.1 → 1.1.1

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 (183) hide show
  1. package/.cursor/plans/unifier-flowresource-avec-flowderivation-c9506e24.plan.md +372 -0
  2. package/README.md +17 -1
  3. package/biome.json +4 -1
  4. package/dist/picoflow.js +1155 -582
  5. package/dist/types/flow/base/flowDisposable.d.ts +67 -0
  6. package/dist/types/flow/base/flowDisposable.d.ts.map +1 -0
  7. package/dist/types/flow/base/flowEffect.d.ts +127 -0
  8. package/dist/types/flow/base/flowEffect.d.ts.map +1 -0
  9. package/dist/types/flow/base/flowGraph.d.ts +97 -0
  10. package/dist/types/flow/base/flowGraph.d.ts.map +1 -0
  11. package/dist/types/flow/base/flowSignal.d.ts +134 -0
  12. package/dist/types/flow/base/flowSignal.d.ts.map +1 -0
  13. package/dist/types/flow/base/flowTracker.d.ts +15 -0
  14. package/dist/types/flow/base/flowTracker.d.ts.map +1 -0
  15. package/dist/types/flow/base/index.d.ts +7 -0
  16. package/dist/types/flow/base/index.d.ts.map +1 -0
  17. package/dist/types/flow/base/utils.d.ts +20 -0
  18. package/dist/types/flow/base/utils.d.ts.map +1 -0
  19. package/dist/types/{advanced/array.d.ts → flow/collections/flowArray.d.ts} +50 -12
  20. package/dist/types/flow/collections/flowArray.d.ts.map +1 -0
  21. package/dist/types/flow/collections/flowMap.d.ts +224 -0
  22. package/dist/types/flow/collections/flowMap.d.ts.map +1 -0
  23. package/dist/types/flow/collections/index.d.ts +3 -0
  24. package/dist/types/flow/collections/index.d.ts.map +1 -0
  25. package/dist/types/flow/index.d.ts +4 -0
  26. package/dist/types/flow/index.d.ts.map +1 -0
  27. package/dist/types/flow/nodes/async/flowConstantAsync.d.ts +137 -0
  28. package/dist/types/flow/nodes/async/flowConstantAsync.d.ts.map +1 -0
  29. package/dist/types/flow/nodes/async/flowDerivationAsync.d.ts +137 -0
  30. package/dist/types/flow/nodes/async/flowDerivationAsync.d.ts.map +1 -0
  31. package/dist/types/flow/nodes/async/flowNodeAsync.d.ts +343 -0
  32. package/dist/types/flow/nodes/async/flowNodeAsync.d.ts.map +1 -0
  33. package/dist/types/flow/nodes/async/flowReadonlyAsync.d.ts +81 -0
  34. package/dist/types/flow/nodes/async/flowReadonlyAsync.d.ts.map +1 -0
  35. package/dist/types/flow/nodes/async/flowStateAsync.d.ts +111 -0
  36. package/dist/types/flow/nodes/async/flowStateAsync.d.ts.map +1 -0
  37. package/dist/types/flow/nodes/async/index.d.ts +6 -0
  38. package/dist/types/flow/nodes/async/index.d.ts.map +1 -0
  39. package/dist/types/flow/nodes/index.d.ts +3 -0
  40. package/dist/types/flow/nodes/index.d.ts.map +1 -0
  41. package/dist/types/flow/nodes/sync/flowConstant.d.ts +108 -0
  42. package/dist/types/flow/nodes/sync/flowConstant.d.ts.map +1 -0
  43. package/dist/types/flow/nodes/sync/flowDerivation.d.ts +100 -0
  44. package/dist/types/flow/nodes/sync/flowDerivation.d.ts.map +1 -0
  45. package/dist/types/flow/nodes/sync/flowNode.d.ts +314 -0
  46. package/dist/types/flow/nodes/sync/flowNode.d.ts.map +1 -0
  47. package/dist/types/flow/nodes/sync/flowReadonly.d.ts +57 -0
  48. package/dist/types/flow/nodes/sync/flowReadonly.d.ts.map +1 -0
  49. package/dist/types/flow/nodes/sync/flowState.d.ts +96 -0
  50. package/dist/types/flow/nodes/sync/flowState.d.ts.map +1 -0
  51. package/dist/types/flow/nodes/sync/index.d.ts +6 -0
  52. package/dist/types/flow/nodes/sync/index.d.ts.map +1 -0
  53. package/dist/types/index.d.ts +2 -4
  54. package/dist/types/index.d.ts.map +1 -1
  55. package/dist/types/solid/converters.d.ts +34 -45
  56. package/dist/types/solid/converters.d.ts.map +1 -1
  57. package/dist/types/solid/index.d.ts +2 -2
  58. package/dist/types/solid/index.d.ts.map +1 -1
  59. package/dist/types/solid/primitives.d.ts +1 -0
  60. package/dist/types/solid/primitives.d.ts.map +1 -1
  61. package/docs/.vitepress/config.mts +1 -1
  62. package/docs/api/typedoc-sidebar.json +81 -1
  63. package/package.json +60 -58
  64. package/src/flow/base/flowDisposable.ts +71 -0
  65. package/src/flow/base/flowEffect.ts +171 -0
  66. package/src/flow/base/flowGraph.ts +288 -0
  67. package/src/flow/base/flowSignal.ts +207 -0
  68. package/src/flow/base/flowTracker.ts +17 -0
  69. package/src/flow/base/index.ts +6 -0
  70. package/src/flow/base/utils.ts +19 -0
  71. package/src/flow/collections/flowArray.ts +409 -0
  72. package/src/flow/collections/flowMap.ts +398 -0
  73. package/src/flow/collections/index.ts +2 -0
  74. package/src/flow/index.ts +3 -0
  75. package/src/flow/nodes/async/flowConstantAsync.ts +142 -0
  76. package/src/flow/nodes/async/flowDerivationAsync.ts +143 -0
  77. package/src/flow/nodes/async/flowNodeAsync.ts +474 -0
  78. package/src/flow/nodes/async/flowReadonlyAsync.ts +81 -0
  79. package/src/flow/nodes/async/flowStateAsync.ts +116 -0
  80. package/src/flow/nodes/async/index.ts +5 -0
  81. package/src/flow/nodes/await/advanced/index.ts +5 -0
  82. package/src/{advanced → flow/nodes/await/advanced}/resource.ts +37 -3
  83. package/src/{advanced → flow/nodes/await/advanced}/resourceAsync.ts +35 -3
  84. package/src/{advanced → flow/nodes/await/advanced}/stream.ts +40 -2
  85. package/src/{advanced → flow/nodes/await/advanced}/streamAsync.ts +38 -3
  86. package/src/flow/nodes/await/flowConstantAwait.ts +154 -0
  87. package/src/flow/nodes/await/flowDerivationAwait.ts +154 -0
  88. package/src/flow/nodes/await/flowNodeAwait.ts +508 -0
  89. package/src/flow/nodes/await/flowReadonlyAwait.ts +89 -0
  90. package/src/flow/nodes/await/flowStateAwait.ts +130 -0
  91. package/src/flow/nodes/await/index.ts +5 -0
  92. package/src/flow/nodes/index.ts +3 -0
  93. package/src/flow/nodes/sync/flowConstant.ts +111 -0
  94. package/src/flow/nodes/sync/flowDerivation.ts +105 -0
  95. package/src/flow/nodes/sync/flowNode.ts +439 -0
  96. package/src/flow/nodes/sync/flowReadonly.ts +57 -0
  97. package/src/flow/nodes/sync/flowState.ts +101 -0
  98. package/src/flow/nodes/sync/index.ts +5 -0
  99. package/src/index.ts +2 -47
  100. package/src/solid/converters.ts +60 -199
  101. package/src/solid/index.ts +2 -8
  102. package/src/solid/primitives.ts +4 -0
  103. package/test/base/flowEffect.test.ts +108 -0
  104. package/test/base/flowGraph.test.ts +485 -0
  105. package/test/base/flowSignal.test.ts +372 -0
  106. package/test/collections/flowArray.asyncStates.test.ts +1553 -0
  107. package/test/collections/flowArray.scalars.test.ts +1129 -0
  108. package/test/collections/flowArray.states.test.ts +1365 -0
  109. package/test/collections/flowMap.asyncStates.test.ts +1105 -0
  110. package/test/collections/flowMap.scalars.test.ts +877 -0
  111. package/test/collections/flowMap.states.test.ts +1097 -0
  112. package/test/nodes/async/flowConstantAsync.test.ts +860 -0
  113. package/test/nodes/async/flowDerivationAsync.test.ts +1517 -0
  114. package/test/nodes/async/flowStateAsync.test.ts +1387 -0
  115. package/test/{resource.test.ts → nodes/await/advanced/resource.test.ts} +21 -19
  116. package/test/{resourceAsync.test.ts → nodes/await/advanced/resourceAsync.test.ts} +3 -1
  117. package/test/{stream.test.ts → nodes/await/advanced/stream.test.ts} +30 -28
  118. package/test/{streamAsync.test.ts → nodes/await/advanced/streamAsync.test.ts} +16 -14
  119. package/test/nodes/await/flowConstantAwait.test.ts +643 -0
  120. package/test/nodes/await/flowDerivationAwait.test.ts +1583 -0
  121. package/test/nodes/await/flowStateAwait.test.ts +999 -0
  122. package/test/nodes/mixed/derivation.test.ts +1527 -0
  123. package/test/nodes/sync/flowConstant.test.ts +620 -0
  124. package/test/nodes/sync/flowDerivation.test.ts +1373 -0
  125. package/test/nodes/sync/flowState.test.ts +945 -0
  126. package/test/solid/converters.test.ts +721 -0
  127. package/test/solid/primitives.test.ts +1031 -0
  128. package/tsconfig.json +2 -1
  129. package/vitest.config.ts +7 -1
  130. package/IMPLEMENTATION_GUIDE.md +0 -1578
  131. package/dist/types/advanced/array.d.ts.map +0 -1
  132. package/dist/types/advanced/index.d.ts +0 -9
  133. package/dist/types/advanced/index.d.ts.map +0 -1
  134. package/dist/types/advanced/map.d.ts +0 -166
  135. package/dist/types/advanced/map.d.ts.map +0 -1
  136. package/dist/types/advanced/resource.d.ts +0 -78
  137. package/dist/types/advanced/resource.d.ts.map +0 -1
  138. package/dist/types/advanced/resourceAsync.d.ts +0 -56
  139. package/dist/types/advanced/resourceAsync.d.ts.map +0 -1
  140. package/dist/types/advanced/stream.d.ts +0 -117
  141. package/dist/types/advanced/stream.d.ts.map +0 -1
  142. package/dist/types/advanced/streamAsync.d.ts +0 -97
  143. package/dist/types/advanced/streamAsync.d.ts.map +0 -1
  144. package/dist/types/basic/constant.d.ts +0 -60
  145. package/dist/types/basic/constant.d.ts.map +0 -1
  146. package/dist/types/basic/derivation.d.ts +0 -89
  147. package/dist/types/basic/derivation.d.ts.map +0 -1
  148. package/dist/types/basic/disposable.d.ts +0 -82
  149. package/dist/types/basic/disposable.d.ts.map +0 -1
  150. package/dist/types/basic/effect.d.ts +0 -67
  151. package/dist/types/basic/effect.d.ts.map +0 -1
  152. package/dist/types/basic/index.d.ts +0 -10
  153. package/dist/types/basic/index.d.ts.map +0 -1
  154. package/dist/types/basic/observable.d.ts +0 -83
  155. package/dist/types/basic/observable.d.ts.map +0 -1
  156. package/dist/types/basic/signal.d.ts +0 -69
  157. package/dist/types/basic/signal.d.ts.map +0 -1
  158. package/dist/types/basic/state.d.ts +0 -47
  159. package/dist/types/basic/state.d.ts.map +0 -1
  160. package/dist/types/basic/trackingContext.d.ts +0 -33
  161. package/dist/types/basic/trackingContext.d.ts.map +0 -1
  162. package/dist/types/creators.d.ts +0 -340
  163. package/dist/types/creators.d.ts.map +0 -1
  164. package/src/advanced/array.ts +0 -222
  165. package/src/advanced/index.ts +0 -12
  166. package/src/advanced/map.ts +0 -193
  167. package/src/basic/constant.ts +0 -97
  168. package/src/basic/derivation.ts +0 -147
  169. package/src/basic/disposable.ts +0 -86
  170. package/src/basic/effect.ts +0 -104
  171. package/src/basic/index.ts +0 -9
  172. package/src/basic/observable.ts +0 -109
  173. package/src/basic/signal.ts +0 -145
  174. package/src/basic/state.ts +0 -60
  175. package/src/basic/trackingContext.ts +0 -45
  176. package/src/creators.ts +0 -395
  177. package/test/array.test.ts +0 -600
  178. package/test/constant.test.ts +0 -44
  179. package/test/derivation.test.ts +0 -539
  180. package/test/effect.test.ts +0 -29
  181. package/test/map.test.ts +0 -240
  182. package/test/signal.test.ts +0 -72
  183. package/test/state.test.ts +0 -212
@@ -1,340 +0,0 @@
1
- import { FlowMap, FlowResource, FlowResourceAsync, FlowStream, FlowStreamAsync } from './advanced/';
2
- import { FlowArray } from './advanced/array';
3
- import { TrackingContext, FlowConstant, FlowDerivation, FlowEffect, FlowSignal, FlowState } from './basic/';
4
- /**
5
- * Creates a new reactive signal.
6
- *
7
- * @returns A new instance of {@link FlowSignal}.
8
- *
9
- * @remarks
10
- * A signal is the simplest reactive primitive - it doesn't hold a value, but can be triggered
11
- * to notify dependent effects and derivations. Use signals when you need event-like notifications
12
- * without associated data.
13
- *
14
- * @example
15
- * ```typescript
16
- * const $refresh = signal();
17
- *
18
- * effect((t) => {
19
- * $refresh.watch(t);
20
- * console.log('Refreshing...');
21
- * });
22
- *
23
- * $refresh.trigger(); // Logs: "Refreshing..."
24
- * ```
25
- *
26
- * @public
27
- */
28
- export declare function signal(): FlowSignal;
29
- /**
30
- * Creates a new reactive constant.
31
- *
32
- * @typeParam T - The type of the constant value.
33
- * @param value - The value or a function that returns the value (for lazy initialization).
34
- * @returns A new instance of {@link FlowConstant}.
35
- *
36
- * @remarks
37
- * A constant is an immutable reactive value that never changes after initialization.
38
- * It can be initialized eagerly (direct value) or lazily (function). Use constants for
39
- * configuration, computed-once values, or expensive initialization that should only run once.
40
- *
41
- * @example
42
- * ```typescript
43
- * // Eager initialization
44
- * const $config = constant({ apiUrl: 'https://api.example.com' });
45
- *
46
- * // Lazy initialization
47
- * const $computed = constant(() => expensiveCalculation());
48
- * ```
49
- *
50
- * @public
51
- */
52
- export declare function constant<T>(value: T | (() => T)): FlowConstant<T>;
53
- /**
54
- * Creates a new reactive state holding a mutable value.
55
- *
56
- * @typeParam T - The type of the state value.
57
- * @param value - The initial value for the state, or a function returning the initial value.
58
- * @returns A new instance of {@link FlowState}.
59
- *
60
- * @remarks
61
- * State is the most common reactive primitive - a mutable container that notifies dependents
62
- * when its value changes. Use `set()` to update the value and `get(t)` or `pick()` to read it.
63
- *
64
- * @example
65
- * ```typescript
66
- * const $count = state(0);
67
- *
68
- * effect((t) => {
69
- * console.log($count.get(t));
70
- * });
71
- *
72
- * $count.set(1); // Logs: 1
73
- * $count.set(n => n + 1); // Logs: 2
74
- * ```
75
- *
76
- * @public
77
- */
78
- export declare function state<T>(value: T | (() => T)): FlowState<T>;
79
- /**
80
- * Creates a new reactive resource that asynchronously fetches its value, returning `T | undefined`.
81
- *
82
- * @typeParam T - The type of the resource value.
83
- * @param fn - An asynchronous function that fetches the resource value.
84
- * @returns A new instance of {@link FlowResource}.
85
- *
86
- * @remarks
87
- * A resource manages async data fetching with reactive updates. Unlike {@link resourceAsync},
88
- * this returns the resolved value directly (or `undefined` if not fetched yet), making it
89
- * easier to work with in synchronous contexts. Call `fetch()` to trigger the async operation.
90
- *
91
- * @example
92
- * ```typescript
93
- * const $user = resource(() => fetch('/api/user').then(r => r.json()));
94
- *
95
- * // Trigger fetch
96
- * await $user.fetch();
97
- *
98
- * // Use in effect
99
- * effect((t) => {
100
- * const user = $user.get(t);
101
- * if (user) {
102
- * console.log(user.name);
103
- * }
104
- * });
105
- * ```
106
- *
107
- * @public
108
- */
109
- export declare function resource<T>(fn: () => Promise<T>): FlowResource<T>;
110
- /**
111
- * Creates a new reactive asynchronous resource that always returns a Promise.
112
- *
113
- * @typeParam T - The type of the resource value.
114
- * @param fn - An asynchronous function that fetches the resource value.
115
- * @returns A new instance of {@link FlowResourceAsync}.
116
- *
117
- * @remarks
118
- * An async resource manages async data fetching and always returns a Promise, making it
119
- * ideal for async/await patterns. Unlike {@link resource}, the Promise is created lazily
120
- * on first access and cached. Call `fetch()` to create a new Promise and trigger a refetch.
121
- *
122
- * @example
123
- * ```typescript
124
- * const $data = resourceAsync(() => fetch('/api/data').then(r => r.json()));
125
- *
126
- * // Use with async/await
127
- * effect(async (t) => {
128
- * const data = await $data.get(t);
129
- * console.log(data);
130
- * });
131
- *
132
- * // Refetch
133
- * await $data.fetch();
134
- * ```
135
- *
136
- * @public
137
- */
138
- export declare function resourceAsync<T>(fn: () => Promise<T>): FlowResourceAsync<T>;
139
- /**
140
- * Creates a new reactive stream that bridges external event sources with PicoFlow's reactive system.
141
- *
142
- * @typeParam T - The type of the stream value.
143
- * @param updater - A function that receives a setter to update the stream's value.
144
- * It should return a disposer function to clean up resources.
145
- * @returns A new instance of {@link FlowStream}.
146
- *
147
- * @remarks
148
- * Streams are ideal for integrating push-based data sources like WebSockets, DOM events,
149
- * timers, or any event emitter. The updater sets up subscriptions and calls the setter
150
- * when new data arrives. The returned disposer is called on cleanup.
151
- *
152
- * @example
153
- * ```typescript
154
- * // WebSocket stream
155
- * const $messages = stream<string>((set) => {
156
- * const ws = new WebSocket('ws://example.com');
157
- * ws.onmessage = (e) => set(e.data);
158
- * return () => ws.close();
159
- * });
160
- *
161
- * // Timer stream
162
- * const $tick = stream<number>((set) => {
163
- * let count = 0;
164
- * const id = setInterval(() => set(count++), 1000);
165
- * return () => clearInterval(id);
166
- * });
167
- * ```
168
- *
169
- * @public
170
- */
171
- export declare function stream<T>(updater: (set: (value: T) => void) => () => void): FlowStream<T>;
172
- /**
173
- * Creates a new reactive asynchronous stream that always returns a Promise.
174
- *
175
- * @typeParam T - The type of the stream value.
176
- * @param updater - A function that receives a setter to update the stream's value.
177
- * It should return a disposer function to clean up resources.
178
- * @returns A new instance of {@link FlowStreamAsync}.
179
- *
180
- * @remarks
181
- * Async streams are ideal for push-based async data sources where you want to use async/await.
182
- * Unlike {@link stream}, this always returns a Promise that resolves to the value. The initial
183
- * Promise is created on construction and resolves when the setter is first called.
184
- *
185
- * @example
186
- * ```typescript
187
- * const $asyncMessages = streamAsync<string>((set) => {
188
- * const ws = new WebSocket('ws://example.com');
189
- * ws.onmessage = (e) => set(e.data);
190
- * return () => ws.close();
191
- * });
192
- *
193
- * effect(async (t) => {
194
- * const message = await $asyncMessages.get(t);
195
- * console.log('Received:', message);
196
- * });
197
- * ```
198
- *
199
- * @public
200
- */
201
- export declare function streamAsync<T>(updater: (set: (value: T) => void) => () => void): FlowStreamAsync<T>;
202
- /**
203
- * Creates a new reactive derivation whose value is computed based on other reactive signals.
204
- *
205
- * @typeParam T - The type of the derived value.
206
- * @param fn - A function that computes the derived value using a tracking context.
207
- * @returns A new instance of {@link FlowDerivation}.
208
- *
209
- * @remarks
210
- * A derivation is a computed reactive value that automatically tracks its dependencies and
211
- * recomputes when they change. The computation is lazy - it runs only when the value is
212
- * accessed, not on construction. Use derivations to create derived state without manual
213
- * dependency management.
214
- *
215
- * @example
216
- * ```typescript
217
- * const $firstName = state('John');
218
- * const $lastName = state('Doe');
219
- *
220
- * const $fullName = derivation((t) => {
221
- * return `${$firstName.get(t)} ${$lastName.get(t)}`;
222
- * });
223
- *
224
- * effect((t) => {
225
- * console.log($fullName.get(t)); // Logs: "John Doe"
226
- * });
227
- *
228
- * $firstName.set('Jane'); // Logs: "Jane Doe"
229
- * ```
230
- *
231
- * @public
232
- */
233
- export declare function derivation<T>(fn: (t: TrackingContext) => T): FlowDerivation<T>;
234
- /**
235
- * Creates a new reactive effect that executes a side-effect function based on its dependencies.
236
- *
237
- * @param fn - A function that performs side effects using a tracking context.
238
- * @returns A new instance of {@link FlowEffect}.
239
- *
240
- * @remarks
241
- * An effect is a reactive computation that runs immediately and re-runs whenever its tracked
242
- * dependencies change. Use effects for side effects like logging, DOM updates, network requests,
243
- * or any operation that should respond to reactive state changes.
244
- *
245
- * The effect executes immediately upon creation and provides a tracking context (`t`) that you
246
- * use to explicitly mark dependencies via `observable.get(t)`. Use `observable.pick()` for
247
- * reads that shouldn't trigger re-runs.
248
- *
249
- * @example
250
- * ```typescript
251
- * const $count = state(0);
252
- *
253
- * const fx = effect((t) => {
254
- * console.log('Count is:', $count.get(t));
255
- * });
256
- *
257
- * $count.set(1); // Logs: "Count is: 1"
258
- * $count.set(2); // Logs: "Count is: 2"
259
- *
260
- * // Clean up when done
261
- * fx.dispose();
262
- * ```
263
- *
264
- * @public
265
- */
266
- export declare function effect(fn: (t: TrackingContext) => void): FlowEffect;
267
- /**
268
- * Creates a new reactive map state with fine-grained tracking of operations.
269
- *
270
- * @typeParam K - The type of the keys.
271
- * @typeParam V - The type of the values.
272
- * @param initial - An optional record of key-value pairs to initialize the map.
273
- * @returns A new instance of {@link FlowMap}.
274
- *
275
- * @remarks
276
- * A reactive map wraps a native JavaScript Map and provides multiple levels of reactivity:
277
- * tracking the entire map, tracking individual set operations, and tracking individual
278
- * delete operations. The initial record (if provided) is converted to a native Map.
279
- *
280
- * @example
281
- * ```typescript
282
- * const $users = map<string, User>({
283
- * 'user1': { name: 'John', age: 30 }
284
- * });
285
- *
286
- * // Track the whole map
287
- * effect((t) => {
288
- * console.log('Users:', $users.get(t).size);
289
- * });
290
- *
291
- * // Track additions
292
- * effect((t) => {
293
- * const { key, value } = $users.$lastSet.get(t);
294
- * if (key) console.log(`Added: ${key}`);
295
- * });
296
- *
297
- * $users.setAt('user2', { name: 'Jane', age: 25 });
298
- * ```
299
- *
300
- * @public
301
- */
302
- export declare function map<K extends string | number | symbol, V>(initial?: Record<K, V>): FlowMap<K, V>;
303
- /**
304
- * Creates a new reactive array with mutation methods and fine-grained action tracking.
305
- *
306
- * @typeParam T - The type of the array elements.
307
- * @param initial - An optional array of initial values.
308
- * @returns A new instance of {@link FlowArray}.
309
- *
310
- * @remarks
311
- * A reactive array provides array-like mutation methods (push, pop, shift, unshift, splice)
312
- * and tracks the last operation performed via `$lastAction`. This enables both whole-array
313
- * reactivity and fine-grained tracking of specific mutations.
314
- *
315
- * The array automatically disposes disposable items when they are removed (if they implement
316
- * the FlowDisposable interface).
317
- *
318
- * @example
319
- * ```typescript
320
- * const $items = array([1, 2, 3]);
321
- *
322
- * // Track the whole array
323
- * effect((t) => {
324
- * console.log('Items:', $items.get(t));
325
- * });
326
- *
327
- * // Track the last action
328
- * effect((t) => {
329
- * const action = $items.$lastAction.get(t);
330
- * console.log('Action:', action.type);
331
- * });
332
- *
333
- * $items.push(4); // Logs action: "push"
334
- * $items.pop(); // Logs action: "pop"
335
- * ```
336
- *
337
- * @public
338
- */
339
- export declare function array<T>(initial?: T[]): FlowArray<T>;
340
- //# sourceMappingURL=creators.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"creators.d.ts","sourceRoot":"","sources":["../../src/creators.ts"],"names":[],"mappings":"AAAA,OAAO,EACN,OAAO,EACP,YAAY,EACZ,iBAAiB,EACjB,UAAU,EACV,eAAe,EACf,MAAM,aAAa,CAAC;AACrB,OAAO,EAAE,SAAS,EAAE,MAAM,kBAAkB,CAAC;AAC7C,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,UAAU,CAAC;AAChD,OAAO,EACN,YAAY,EACZ,cAAc,EACd,UAAU,EACV,UAAU,EACV,SAAS,EACT,MAAM,UAAU,CAAC;AAElB;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,wBAAgB,MAAM,IAAI,UAAU,CAEnC;AAED;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,wBAAgB,QAAQ,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC,GAAG,YAAY,CAAC,CAAC,CAAC,CAEjE;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,wBAAgB,KAAK,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC,GAAG,SAAS,CAAC,CAAC,CAAC,CAE3D;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6BG;AACH,wBAAgB,QAAQ,CAAC,CAAC,EAAE,EAAE,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GAAG,YAAY,CAAC,CAAC,CAAC,CAEjE;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,wBAAgB,aAAa,CAAC,CAAC,EAAE,EAAE,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GAAG,iBAAiB,CAAC,CAAC,CAAC,CAE3E;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;AACH,wBAAgB,MAAM,CAAC,CAAC,EACvB,OAAO,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,EAAE,CAAC,KAAK,IAAI,KAAK,MAAM,IAAI,GAC9C,UAAU,CAAC,CAAC,CAAC,CAEf;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4BG;AACH,wBAAgB,WAAW,CAAC,CAAC,EAC5B,OAAO,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,EAAE,CAAC,KAAK,IAAI,KAAK,MAAM,IAAI,GAC9C,eAAe,CAAC,CAAC,CAAC,CAEpB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AACH,wBAAgB,UAAU,CAAC,CAAC,EAC3B,EAAE,EAAE,CAAC,CAAC,EAAE,eAAe,KAAK,CAAC,GAC3B,cAAc,CAAC,CAAC,CAAC,CAEnB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;AACH,wBAAgB,MAAM,CAAC,EAAE,EAAE,CAAC,CAAC,EAAE,eAAe,KAAK,IAAI,GAAG,UAAU,CAEnE;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkCG;AACH,wBAAgB,GAAG,CAAC,CAAC,SAAS,MAAM,GAAG,MAAM,GAAG,MAAM,EAAE,CAAC,EACxD,OAAO,CAAC,EAAE,MAAM,CAAC,CAAC,EAAE,CAAC,CAAC,GACpB,OAAO,CAAC,CAAC,EAAE,CAAC,CAAC,CAIf;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAmCG;AACH,wBAAgB,KAAK,CAAC,CAAC,EAAE,OAAO,CAAC,EAAE,CAAC,EAAE,GAAG,SAAS,CAAC,CAAC,CAAC,CAEpD"}
@@ -1,222 +0,0 @@
1
- import { FlowObservable, type FlowState, isDisposable } from "../basic";
2
- import { state } from "../creators";
3
-
4
- /**
5
- * Represents the actions that can be performed on a FlowArray.
6
- * @public
7
- */
8
- export type FlowArrayAction<T> =
9
- | {
10
- type: "set";
11
- items: T[];
12
- }
13
- | {
14
- type: "setItem";
15
- index: number;
16
- item: T;
17
- }
18
- | {
19
- type: "push";
20
- item: T;
21
- }
22
- | {
23
- type: "pop";
24
- }
25
- | {
26
- type: "unshift";
27
- item: T;
28
- }
29
- | {
30
- type: "shift";
31
- }
32
- | {
33
- type: "splice";
34
- start: number;
35
- deleteCount: number;
36
- items: T[];
37
- }
38
- | {
39
- type: "clear";
40
- };
41
-
42
- /**
43
- * Represents a reactive array.
44
- * @public
45
- */
46
- export class FlowArray<T> extends FlowObservable<T[]> {
47
- /**
48
- * Last action performed on the FlowArray.
49
- * @public
50
- */
51
- $lastAction: FlowState<FlowArrayAction<T>>;
52
-
53
- /**
54
- * Creates an instance of FlowArray.
55
- * @param value - Initial array value.
56
- * @public
57
- */
58
- constructor(value: T[] = []) {
59
- super();
60
- this._value = value;
61
- this.$lastAction = state<FlowArrayAction<T>>({
62
- type: "set",
63
- items: value,
64
- });
65
- }
66
-
67
- /**
68
- * Gets the current length of the array.
69
- * @returns The length of the array.
70
- * @public
71
- */
72
- get length(): number {
73
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
74
- return this._value.length;
75
- }
76
-
77
- /**
78
- * Internal method to get the raw value.
79
- * @internal
80
- */
81
- protected _getRaw(): T[] {
82
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
83
- return [...this._value]; // Ensure nobody can modify the original array
84
- }
85
-
86
- /**
87
- * Replaces the entire array with new items.
88
- * @param items - The new array of items.
89
- * @public
90
- */
91
- set(items: T[]): void {
92
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
93
- this._value.forEach((item) => {
94
- if (isDisposable(item)) item.dispose({ self: true });
95
- });
96
- this._value = items;
97
- this._notify();
98
- this.$lastAction.set({ type: "set", items: items });
99
- }
100
-
101
- /**
102
- * Replaces an item at a specific index.
103
- * @param index - The index of the item to replace.
104
- * @param item - The new item.
105
- * @public
106
- */
107
- setItem(index: number, item: T): void {
108
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
109
- if (index < 0 || index >= this._value.length) {
110
- throw new Error("[PicoFlow] Index out of bounds");
111
- }
112
- this._value[index] = item;
113
- this._notify();
114
- this.$lastAction.set({ type: "setItem", index: index, item: item });
115
- }
116
-
117
- /**
118
- * Appends an item to the end of the array.
119
- * @param item - The item to append.
120
- * @public
121
- */
122
- push(item: T): void {
123
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
124
- this._value.push(item);
125
- this._notify();
126
- this.$lastAction.set({ type: "push", item: item });
127
- }
128
-
129
- /**
130
- * Removes the last item from the array.
131
- * @public
132
- */
133
- pop(): void {
134
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
135
- const item = this._value.pop();
136
- if (isDisposable(item)) {
137
- item.dispose({ self: true });
138
- }
139
- this._notify();
140
- this.$lastAction.set({ type: "pop" });
141
- }
142
-
143
- /**
144
- * Inserts an item at the beginning of the array.
145
- * @param item - The item to insert.
146
- * @public
147
- */
148
- unshift(item: T): void {
149
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
150
- this._value.unshift(item);
151
- this._notify();
152
- this.$lastAction.set({ type: "unshift", item: item });
153
- }
154
-
155
- /**
156
- * Removes the first item from the array.
157
- * @public
158
- */
159
- shift(): void {
160
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
161
- const item = this._value.shift();
162
- if (isDisposable(item)) {
163
- item.dispose({ self: true });
164
- }
165
- this._notify();
166
- this.$lastAction.set({ type: "shift" });
167
- }
168
-
169
- /**
170
- * Changes the content of the array.
171
- * @param start - The starting index.
172
- * @param deleteCount - Number of items to remove.
173
- * @param newItems - New items to add.
174
- * @public
175
- */
176
- splice(start: number, deleteCount: number, ...newItems: T[]): void {
177
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
178
- const items = this._value.splice(start, deleteCount, ...newItems);
179
- items.forEach((item) => {
180
- if (isDisposable(item)) item.dispose({ self: true });
181
- });
182
- this._notify();
183
- this.$lastAction.set({
184
- type: "splice",
185
- start: start,
186
- deleteCount: deleteCount,
187
- items: newItems,
188
- });
189
- }
190
-
191
- /**
192
- * Clears all items from the array.
193
- * @public
194
- */
195
- clear(): void {
196
- if (this._disposed) throw new Error("[PicoFlow] Primitive is disposed");
197
- const items = [...this._value];
198
- items.forEach((item) => {
199
- if (isDisposable(item)) item.dispose({ self: true });
200
- });
201
- this._value = [];
202
- this._notify();
203
- this.$lastAction.set({ type: "clear" });
204
- }
205
-
206
- /**
207
- * Disposes the FlowArray and its items.
208
- * @param options - Disposal options.
209
- * @public
210
- */
211
- override dispose(options?: { self: boolean }): void {
212
- super.dispose(options);
213
- this._value.forEach((item) => {
214
- if (isDisposable(item)) item.dispose(options);
215
- });
216
- this._value = [];
217
- }
218
-
219
- /* INTERNAL */
220
-
221
- /** @internal */ protected override _value: T[] = [];
222
- }
@@ -1,12 +0,0 @@
1
- export type { FlowArrayAction } from "./array";
2
- export { FlowArray } from "./array";
3
- export { FlowMap } from "./map";
4
- export { FlowResource } from "./resource";
5
- export { FlowResourceAsync } from "./resourceAsync";
6
- export type {
7
- FlowStreamDisposer,
8
- FlowStreamSetter,
9
- FlowStreamUpdater,
10
- } from "./stream";
11
- export { FlowStream } from "./stream";
12
- export { FlowStreamAsync } from "./streamAsync";