@fluixi/reactive 1.0.0-alpha.100

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 (211) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +280 -0
  3. package/dist/cdn/reactive.cjs +2803 -0
  4. package/dist/cdn/reactive.d.ts +11 -0
  5. package/dist/cdn/reactive.d.ts.map +1 -0
  6. package/dist/cdn/reactive.global.js +2 -0
  7. package/dist/cdn/reactive.js +10 -0
  8. package/dist/cdn/reactive.mjs +2787 -0
  9. package/dist/cdn/signal.cjs +299 -0
  10. package/dist/cdn/signal.d.ts +19 -0
  11. package/dist/cdn/signal.d.ts.map +1 -0
  12. package/dist/cdn/signal.global.js +2 -0
  13. package/dist/cdn/signal.js +18 -0
  14. package/dist/cdn/signal.mjs +276 -0
  15. package/dist/index.cjs +2803 -0
  16. package/dist/index.d.ts +2 -0
  17. package/dist/index.d.ts.map +1 -0
  18. package/dist/index.js +1 -0
  19. package/dist/index.mjs +2787 -0
  20. package/dist/lib/index.cjs +2804 -0
  21. package/dist/lib/index.d.ts +8 -0
  22. package/dist/lib/index.d.ts.map +1 -0
  23. package/dist/lib/index.js +11 -0
  24. package/dist/lib/index.mjs +2789 -0
  25. package/dist/lib/observable/index.cjs +386 -0
  26. package/dist/lib/observable/index.d.ts +4 -0
  27. package/dist/lib/observable/index.d.ts.map +1 -0
  28. package/dist/lib/observable/index.js +3 -0
  29. package/dist/lib/observable/index.mjs +364 -0
  30. package/dist/lib/observable/observable.cjs +384 -0
  31. package/dist/lib/observable/observable.d.ts +246 -0
  32. package/dist/lib/observable/observable.d.ts.map +1 -0
  33. package/dist/lib/observable/observable.js +268 -0
  34. package/dist/lib/observable/observable.mjs +361 -0
  35. package/dist/lib/observable/subscription.cjs +180 -0
  36. package/dist/lib/observable/subscription.d.ts +58 -0
  37. package/dist/lib/observable/subscription.d.ts.map +1 -0
  38. package/dist/lib/observable/subscription.js +177 -0
  39. package/dist/lib/observable/subscription.mjs +157 -0
  40. package/dist/lib/observable/types.cjs +18 -0
  41. package/dist/lib/observable/types.d.ts +44 -0
  42. package/dist/lib/observable/types.d.ts.map +1 -0
  43. package/dist/lib/observable/types.js +1 -0
  44. package/dist/lib/observable/types.mjs +0 -0
  45. package/dist/lib/predicates.cjs +44 -0
  46. package/dist/lib/predicates.d.ts +37 -0
  47. package/dist/lib/predicates.d.ts.map +1 -0
  48. package/dist/lib/predicates.js +62 -0
  49. package/dist/lib/predicates.mjs +23 -0
  50. package/dist/lib/signal/api.cjs +592 -0
  51. package/dist/lib/signal/api.d.ts +227 -0
  52. package/dist/lib/signal/api.d.ts.map +1 -0
  53. package/dist/lib/signal/api.js +228 -0
  54. package/dist/lib/signal/api.mjs +569 -0
  55. package/dist/lib/signal/cached-resource.cjs +726 -0
  56. package/dist/lib/signal/cached-resource.d.ts +86 -0
  57. package/dist/lib/signal/cached-resource.d.ts.map +1 -0
  58. package/dist/lib/signal/cached-resource.js +250 -0
  59. package/dist/lib/signal/cached-resource.mjs +704 -0
  60. package/dist/lib/signal/graph/children.cjs +326 -0
  61. package/dist/lib/signal/graph/children.d.ts +2 -0
  62. package/dist/lib/signal/graph/children.d.ts.map +1 -0
  63. package/dist/lib/signal/graph/children.js +30 -0
  64. package/dist/lib/signal/graph/children.mjs +303 -0
  65. package/dist/lib/signal/graph/compat.cjs +590 -0
  66. package/dist/lib/signal/graph/compat.d.ts +66 -0
  67. package/dist/lib/signal/graph/compat.d.ts.map +1 -0
  68. package/dist/lib/signal/graph/compat.js +197 -0
  69. package/dist/lib/signal/graph/compat.mjs +568 -0
  70. package/dist/lib/signal/graph/core.cjs +295 -0
  71. package/dist/lib/signal/graph/core.d.ts +99 -0
  72. package/dist/lib/signal/graph/core.d.ts.map +1 -0
  73. package/dist/lib/signal/graph/core.js +268 -0
  74. package/dist/lib/signal/graph/core.mjs +273 -0
  75. package/dist/lib/signal/graph/debounced.cjs +680 -0
  76. package/dist/lib/signal/graph/debounced.d.ts +67 -0
  77. package/dist/lib/signal/graph/debounced.d.ts.map +1 -0
  78. package/dist/lib/signal/graph/debounced.js +92 -0
  79. package/dist/lib/signal/graph/debounced.mjs +657 -0
  80. package/dist/lib/signal/graph/derived.cjs +508 -0
  81. package/dist/lib/signal/graph/derived.d.ts +14 -0
  82. package/dist/lib/signal/graph/derived.d.ts.map +1 -0
  83. package/dist/lib/signal/graph/derived.js +65 -0
  84. package/dist/lib/signal/graph/derived.mjs +485 -0
  85. package/dist/lib/signal/graph/detect.cjs +66 -0
  86. package/dist/lib/signal/graph/detect.d.ts +17 -0
  87. package/dist/lib/signal/graph/detect.d.ts.map +1 -0
  88. package/dist/lib/signal/graph/detect.js +39 -0
  89. package/dist/lib/signal/graph/detect.mjs +45 -0
  90. package/dist/lib/signal/graph/error-boundary.cjs +313 -0
  91. package/dist/lib/signal/graph/error-boundary.d.ts +16 -0
  92. package/dist/lib/signal/graph/error-boundary.d.ts.map +1 -0
  93. package/dist/lib/signal/graph/error-boundary.js +34 -0
  94. package/dist/lib/signal/graph/error-boundary.mjs +290 -0
  95. package/dist/lib/signal/graph/index.cjs +305 -0
  96. package/dist/lib/signal/graph/index.d.ts +22 -0
  97. package/dist/lib/signal/graph/index.d.ts.map +1 -0
  98. package/dist/lib/signal/graph/index.js +21 -0
  99. package/dist/lib/signal/graph/index.mjs +283 -0
  100. package/dist/lib/signal/graph/observe.cjs +198 -0
  101. package/dist/lib/signal/graph/observe.d.ts +185 -0
  102. package/dist/lib/signal/graph/observe.d.ts.map +1 -0
  103. package/dist/lib/signal/graph/observe.js +198 -0
  104. package/dist/lib/signal/graph/observe.mjs +175 -0
  105. package/dist/lib/signal/graph/resource.cjs +632 -0
  106. package/dist/lib/signal/graph/resource.d.ts +39 -0
  107. package/dist/lib/signal/graph/resource.d.ts.map +1 -0
  108. package/dist/lib/signal/graph/resource.js +165 -0
  109. package/dist/lib/signal/graph/resource.mjs +609 -0
  110. package/dist/lib/signal/graph/runtime.cjs +522 -0
  111. package/dist/lib/signal/graph/runtime.d.ts +80 -0
  112. package/dist/lib/signal/graph/runtime.d.ts.map +1 -0
  113. package/dist/lib/signal/graph/runtime.js +358 -0
  114. package/dist/lib/signal/graph/runtime.mjs +499 -0
  115. package/dist/lib/signal/graph/signal-next.cjs +1249 -0
  116. package/dist/lib/signal/graph/signal-next.d.ts +38 -0
  117. package/dist/lib/signal/graph/signal-next.d.ts.map +1 -0
  118. package/dist/lib/signal/graph/signal-next.js +44 -0
  119. package/dist/lib/signal/graph/signal-next.mjs +1227 -0
  120. package/dist/lib/signal/graph/ssr-hooks.cjs +89 -0
  121. package/dist/lib/signal/graph/ssr-hooks.d.ts +51 -0
  122. package/dist/lib/signal/graph/ssr-hooks.d.ts.map +1 -0
  123. package/dist/lib/signal/graph/ssr-hooks.js +80 -0
  124. package/dist/lib/signal/graph/ssr-hooks.mjs +68 -0
  125. package/dist/lib/signal/graph/state.cjs +72 -0
  126. package/dist/lib/signal/graph/state.d.ts +76 -0
  127. package/dist/lib/signal/graph/state.d.ts.map +1 -0
  128. package/dist/lib/signal/graph/state.js +99 -0
  129. package/dist/lib/signal/graph/state.mjs +49 -0
  130. package/dist/lib/signal/graph/suspense.cjs +313 -0
  131. package/dist/lib/signal/graph/suspense.d.ts +13 -0
  132. package/dist/lib/signal/graph/suspense.d.ts.map +1 -0
  133. package/dist/lib/signal/graph/suspense.js +36 -0
  134. package/dist/lib/signal/graph/suspense.mjs +290 -0
  135. package/dist/lib/signal/index-legacy.cjs +2582 -0
  136. package/dist/lib/signal/index-legacy.d.ts +12 -0
  137. package/dist/lib/signal/index-legacy.d.ts.map +1 -0
  138. package/dist/lib/signal/index-legacy.js +11 -0
  139. package/dist/lib/signal/index-legacy.mjs +2560 -0
  140. package/dist/lib/signal/index.cjs +1350 -0
  141. package/dist/lib/signal/index.d.ts +19 -0
  142. package/dist/lib/signal/index.d.ts.map +1 -0
  143. package/dist/lib/signal/index.js +19 -0
  144. package/dist/lib/signal/index.mjs +1328 -0
  145. package/dist/lib/signal/list.cjs +561 -0
  146. package/dist/lib/signal/list.d.ts +39 -0
  147. package/dist/lib/signal/list.d.ts.map +1 -0
  148. package/dist/lib/signal/list.js +172 -0
  149. package/dist/lib/signal/list.mjs +538 -0
  150. package/dist/lib/signal/resource-api.cjs +638 -0
  151. package/dist/lib/signal/resource-api.d.ts +19 -0
  152. package/dist/lib/signal/resource-api.d.ts.map +1 -0
  153. package/dist/lib/signal/resource-api.js +27 -0
  154. package/dist/lib/signal/resource-api.mjs +615 -0
  155. package/dist/lib/signal/signal.cjs +2035 -0
  156. package/dist/lib/signal/signal.d.ts +303 -0
  157. package/dist/lib/signal/signal.d.ts.map +1 -0
  158. package/dist/lib/signal/signal.js +1233 -0
  159. package/dist/lib/signal/signal.mjs +2012 -0
  160. package/dist/lib/signal/types.cjs +38 -0
  161. package/dist/lib/signal/types.d.ts +133 -0
  162. package/dist/lib/signal/types.d.ts.map +1 -0
  163. package/dist/lib/signal/types.js +38 -0
  164. package/dist/lib/signal/types.mjs +17 -0
  165. package/dist/lib/signal/utilities.cjs +1024 -0
  166. package/dist/lib/signal/utilities.d.ts +247 -0
  167. package/dist/lib/signal/utilities.d.ts.map +1 -0
  168. package/dist/lib/signal/utilities.js +346 -0
  169. package/dist/lib/signal/utilities.mjs +1002 -0
  170. package/dist/lib/store/api.cjs +662 -0
  171. package/dist/lib/store/api.d.ts +40 -0
  172. package/dist/lib/store/api.d.ts.map +1 -0
  173. package/dist/lib/store/api.js +63 -0
  174. package/dist/lib/store/api.mjs +646 -0
  175. package/dist/lib/store/index.cjs +741 -0
  176. package/dist/lib/store/index.d.ts +16 -0
  177. package/dist/lib/store/index.d.ts.map +1 -0
  178. package/dist/lib/store/index.js +13 -0
  179. package/dist/lib/store/index.mjs +726 -0
  180. package/dist/lib/store/setter.types.cjs +18 -0
  181. package/dist/lib/store/setter.types.d.ts +131 -0
  182. package/dist/lib/store/setter.types.d.ts.map +1 -0
  183. package/dist/lib/store/setter.types.js +65 -0
  184. package/dist/lib/store/setter.types.mjs +0 -0
  185. package/dist/lib/store/store.cjs +708 -0
  186. package/dist/lib/store/store.d.ts +142 -0
  187. package/dist/lib/store/store.d.ts.map +1 -0
  188. package/dist/lib/store/store.js +812 -0
  189. package/dist/lib/store/store.mjs +694 -0
  190. package/dist/lib/store/types.cjs +18 -0
  191. package/dist/lib/store/types.d.ts +57 -0
  192. package/dist/lib/store/types.d.ts.map +1 -0
  193. package/dist/lib/store/types.js +1 -0
  194. package/dist/lib/store/types.mjs +0 -0
  195. package/dist/lib/store/utils.cjs +43 -0
  196. package/dist/lib/store/utils.d.ts +13 -0
  197. package/dist/lib/store/utils.d.ts.map +1 -0
  198. package/dist/lib/store/utils.js +29 -0
  199. package/dist/lib/store/utils.mjs +22 -0
  200. package/dist/lib/subject.cjs +450 -0
  201. package/dist/lib/subject.d.ts +14 -0
  202. package/dist/lib/subject.d.ts.map +1 -0
  203. package/dist/lib/subject.js +81 -0
  204. package/dist/lib/subject.mjs +427 -0
  205. package/dist/tsconfig.lib.tsbuildinfo +1 -0
  206. package/dist/version.generated.cjs +27 -0
  207. package/dist/version.generated.d.ts +3 -0
  208. package/dist/version.generated.d.ts.map +1 -0
  209. package/dist/version.generated.js +3 -0
  210. package/dist/version.generated.mjs +7 -0
  211. package/package.json +115 -0
@@ -0,0 +1,227 @@
1
+ import { type Context, type Owner } from './graph/runtime.js';
2
+ import type { Accessor, Setter, SignalOptions } from './signal.js';
3
+ /** A writable reactive value: call it to read, `.set()` to write. */
4
+ export type SignalHandle<T> = Accessor<T> & {
5
+ set: Setter<T>;
6
+ };
7
+ /** A derived value. Read-only, so it is just the accessor. */
8
+ export type MemoHandle<T> = Accessor<T>;
9
+ /**
10
+ * A writable reactive value.
11
+ *
12
+ * The returned function *is* the accessor, with `set` hung off it, so it passes
13
+ * anywhere an accessor is expected and a read is an ordinary call. Reading inside a
14
+ * tracked scope subscribes that scope; reading outside one does not.
15
+ *
16
+ * `options.equals` decides what counts as a change and defaults to `===`. A write that
17
+ * compares equal notifies nobody, which is how a reflect loop or a feedback cycle
18
+ * terminates.
19
+ *
20
+ * @example
21
+ * ```ts
22
+ * const count = signal(0);
23
+ * count(); // 0
24
+ * count.set(1); // write a value
25
+ * count.set((n) => n + 1); // or derive from the previous one
26
+ * ```
27
+ *
28
+ * @example A function value has to be wrapped, because a bare function is read as an
29
+ * updater and called:
30
+ * ```ts
31
+ * const handler = signal<() => void>(() => {});
32
+ * handler.set(() => myCallback); // stores myCallback
33
+ * handler.set(myCallback); // calls myCallback and stores what it returned
34
+ * ```
35
+ *
36
+ * @example Deep values compare by identity unless told otherwise:
37
+ * ```ts
38
+ * const point = signal({ x: 0 }, { equals: (a, b) => a.x === b.x });
39
+ * ```
40
+ */
41
+ export declare function signal<T>(value: T, options?: SignalOptions<T>): SignalHandle<T>;
42
+ export declare function signal<T = undefined>(): SignalHandle<T | undefined>;
43
+ /**
44
+ * A derived value, computed once per change and cached.
45
+ *
46
+ * Lazy and pull-based: the function does not run until something reads the memo, and
47
+ * then not again until one of its own dependencies changes. That is the difference from
48
+ * {@link computed}, which exists to do work rather than to hold a value.
49
+ *
50
+ * `prev` is the previous result, which makes an accumulator cheap without a second
51
+ * signal to hold it.
52
+ *
53
+ * @example
54
+ * ```ts
55
+ * const first = signal('Ada');
56
+ * const last = signal('Lovelace');
57
+ * const full = memo(() => `${first()} ${last()}`);
58
+ * full(); // 'Ada Lovelace', computed now
59
+ * full(); // cached, the function did not run again
60
+ * ```
61
+ *
62
+ * @example Reading the previous value:
63
+ * ```ts
64
+ * const high = memo((prev = 0) => Math.max(prev, reading()), 0);
65
+ * ```
66
+ */
67
+ export declare function memo<T>(fn: (prev?: T) => T, value?: T, options?: SignalOptions<T>): MemoHandle<T>;
68
+ /**
69
+ * Run `fn` now, and again whenever anything it read changes.
70
+ *
71
+ * Dependencies are collected by reading, not declared, so they are whatever the last
72
+ * run actually touched. A branch not taken subscribes to nothing, and a read behind a
73
+ * condition comes and goes with it.
74
+ *
75
+ * Eager. It runs once on creation and again as soon as a dependency is written, in the
76
+ * same task as the write. `batch` is what coalesces a group of writes into one run.
77
+ *
78
+ * Teardown goes through `onCleanup`, which runs before the next execution and once more
79
+ * on disposal. A returned function is **not** teardown: the return value is carried
80
+ * forward as the next call's `prev`, so returning a disposer silently leaks it. The
81
+ * effect is owned by the enclosing {@link root}, so disposing that disposes this.
82
+ *
83
+ * @example
84
+ * ```ts
85
+ * const query = signal('');
86
+ * effect(() => console.log('searching', query()));
87
+ * ```
88
+ *
89
+ * @example Teardown between runs, via onCleanup rather than a return:
90
+ * ```ts
91
+ * effect(() => {
92
+ * const id = setInterval(tick, delay());
93
+ * onCleanup(() => clearInterval(id));
94
+ * });
95
+ * ```
96
+ *
97
+ * @example Writing a signal an effect reads re-triggers it. Break the cycle with
98
+ * `untrack`, or make the write compare equal:
99
+ * ```ts
100
+ * effect(() => save(untrack(() => draft())));
101
+ * ```
102
+ *
103
+ * @returns Its disposer, for an effect created outside a root.
104
+ */
105
+ export declare function effect<T>(fn: (prev?: T) => T | (() => void), value?: T,
106
+ /** `name` is what a devtools graph calls it, as for `signal` and `memo`. */
107
+ options?: {
108
+ name?: string;
109
+ }): () => void;
110
+ /**
111
+ * The rest of the `create` prefix, dropped.
112
+ *
113
+ * Each one calls through to the long name with the same arguments. Both spellings stay
114
+ * and mix freely; the graph does not know which was written.
115
+ *
116
+ * `onCleanup`, `getOwner` and `runWithOwner` keep their names. The rule here is losing
117
+ * a `create` that adds nothing, and none of those three has one; `cleanup` would also
118
+ * lose the sense that it registers a callback rather than performing one now.
119
+ */
120
+ /**
121
+ * An owner scope with an explicit disposer.
122
+ *
123
+ * Every signal, memo, effect and nested scope created while `fn` runs belongs to this
124
+ * one, and `dispose()` takes all of them down together. Without an owner an effect has
125
+ * nothing to tear it down, which is the usual source of a leak.
126
+ *
127
+ * A root created inside another root is attached to it, so disposal is recursive. To
128
+ * detach deliberately, create the root where no owner is current.
129
+ *
130
+ * @example
131
+ * ```ts
132
+ * const stop = root((dispose) => {
133
+ * effect(() => render(state()));
134
+ * onCleanup(() => detachListeners());
135
+ * return dispose;
136
+ * });
137
+ * stop(); // effect and cleanup both run
138
+ * ```
139
+ *
140
+ * @returns Whatever `fn` returns. Return the disposer when the caller needs it.
141
+ */
142
+ export declare function root<T>(fn: (dispose: () => void) => T): T;
143
+ /**
144
+ * The effect form `@fluixi/dom` wires its bindings with.
145
+ *
146
+ * Timing is identical to {@link effect} in this runtime: both are eager, and both
147
+ * re-run in the task that wrote their dependency. The render-versus-commit distinction
148
+ * the name suggests is a DOM-layer concern, not a graph one, so do not reach for this
149
+ * expecting different scheduling.
150
+ *
151
+ * What differs is that it is not reported to devtools. Every DOM binding goes through
152
+ * here, and a graph carrying one node per text node is not a graph anyone reads.
153
+ *
154
+ * @example
155
+ * ```ts
156
+ * renderEffect(() => el.setAttribute('aria-expanded', String(open())));
157
+ * ```
158
+ */
159
+ export declare function renderEffect<T>(fn: (prev?: T) => T | (() => void), value?: T): () => void;
160
+ /**
161
+ * A tracked computation whose result nobody reads.
162
+ *
163
+ * Eager where {@link memo} is lazy. A memo that nothing reads never runs at all, so a
164
+ * memo written for its side effect silently does nothing; this is the form for work
165
+ * that has to happen on every change.
166
+ *
167
+ * Timing matches {@link effect}, and so does ordering: they run in creation order, not
168
+ * in two phases. A `computed` that writes a signal an effect reads has to be created
169
+ * first for the effect to see the settled value.
170
+ *
171
+ * @example
172
+ * ```ts
173
+ * computed(() => {
174
+ * valid.set(email().includes('@')); // derive into another signal
175
+ * });
176
+ * ```
177
+ *
178
+ * @example `prev` threads the last result through, with no signal to hold it:
179
+ * ```ts
180
+ * computed((runs = 0) => {
181
+ * void query();
182
+ * return runs + 1;
183
+ * }, 0);
184
+ * ```
185
+ */
186
+ export declare function computed<T>(fn: (prev?: T) => T, value?: T): void;
187
+ /**
188
+ * A context key: a value passed down an owner tree instead of through props.
189
+ *
190
+ * Lookup walks owners, not the DOM, so a consumer sees whatever provider encloses it
191
+ * reactively. A consumer with no provider above it gets `defaultValue`, which is why
192
+ * supplying one is usually better than handling undefined everywhere.
193
+ *
194
+ * Pass `name`. Unnamed, the key is a bare symbol and a devtools panel has nothing to
195
+ * label the node with.
196
+ *
197
+ * @example
198
+ * ```ts
199
+ * const Theme = context<'light' | 'dark'>('light', 'theme');
200
+ *
201
+ * // provider side, as a component
202
+ * Theme.Provider({ value: 'dark', children: () => renderPage() });
203
+ *
204
+ * // consumer side, anywhere below it
205
+ * const theme = useContext(Theme); // 'dark' here, 'light' with no provider
206
+ * ```
207
+ */
208
+ export declare function context<T>(defaultValue?: T, name?: string): Context<T>;
209
+ /**
210
+ * A child scope of `parent`, created without entering it.
211
+ *
212
+ * Low level, and rarely the right tool. {@link root} both creates a scope and makes it
213
+ * current, which is what almost all code wants. This hands back an owner to hold and
214
+ * enter later with `runWithOwner`, for a scope whose lifetime does not match the call
215
+ * that created it: a cached subtree, or one list row among many.
216
+ *
217
+ * Disposing `parent` disposes this, since it is attached on creation.
218
+ *
219
+ * @example
220
+ * ```ts
221
+ * const scope = childOwner(getOwner());
222
+ * // later, and possibly from another task
223
+ * runWithOwner(scope, () => effect(() => paint(row())));
224
+ * ```
225
+ */
226
+ export declare function childOwner(parent: Owner | null): Owner;
227
+ //# sourceMappingURL=api.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../../../src/lib/signal/api.ts"],"names":[],"mappings":"AAiCA,OAAO,EAIL,KAAK,OAAO,EACZ,KAAK,KAAK,EACX,MAAM,oBAAoB,CAAC;AAC5B,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAEnE,qEAAqE;AACrE,MAAM,MAAM,YAAY,CAAC,CAAC,IAAI,QAAQ,CAAC,CAAC,CAAC,GAAG;IAAE,GAAG,EAAE,MAAM,CAAC,CAAC,CAAC,CAAA;CAAE,CAAC;AAE/D,8DAA8D;AAC9D,MAAM,MAAM,UAAU,CAAC,CAAC,IAAI,QAAQ,CAAC,CAAC,CAAC,CAAC;AAExC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;AACH,wBAAgB,MAAM,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,EAAE,OAAO,CAAC,EAAE,aAAa,CAAC,CAAC,CAAC,GAAG,YAAY,CAAC,CAAC,CAAC,CAAC;AACjF,wBAAgB,MAAM,CAAC,CAAC,GAAG,SAAS,KAAK,YAAY,CAAC,CAAC,GAAG,SAAS,CAAC,CAAC;AAMrE;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,wBAAgB,IAAI,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC,KAAK,CAAC,EAAE,KAAK,CAAC,EAAE,CAAC,EAAE,OAAO,CAAC,EAAE,aAAa,CAAC,CAAC,CAAC,GAAG,UAAU,CAAC,CAAC,CAAC,CAEjG;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAoCG;AACH,wBAAgB,MAAM,CAAC,CAAC,EACtB,EAAE,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC,KAAK,CAAC,GAAG,CAAC,MAAM,IAAI,CAAC,EAClC,KAAK,CAAC,EAAE,CAAC;AACT,4EAA4E;AAC5E,OAAO,CAAC,EAAE;IAAE,IAAI,CAAC,EAAE,MAAM,CAAA;CAAE,GAC1B,MAAM,IAAI,CAEZ;AAED;;;;;;;;;GASG;AAEH;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,wBAAgB,IAAI,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,OAAO,EAAE,MAAM,IAAI,KAAK,CAAC,GAAG,CAAC,CAEzD;AAED;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,YAAY,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC,KAAK,CAAC,GAAG,CAAC,MAAM,IAAI,CAAC,EAAE,KAAK,CAAC,EAAE,CAAC,GAAG,MAAM,IAAI,CAEzF;AAED;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AACH,wBAAgB,QAAQ,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC,KAAK,CAAC,EAAE,KAAK,CAAC,EAAE,CAAC,GAAG,IAAI,CAEhE;AAED;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,wBAAgB,OAAO,CAAC,CAAC,EAAE,YAAY,CAAC,EAAE,CAAC,EAAE,IAAI,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,CAAC,CAAC,CAEtE;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAgB,UAAU,CAAC,MAAM,EAAE,KAAK,GAAG,IAAI,GAAG,KAAK,CAEtD"}
@@ -0,0 +1,228 @@
1
+ /**
2
+ * The short reactive API: the `create` prefix dropped, where dropping it loses nothing.
3
+ *
4
+ * signal memo effect root renderEffect computed context childOwner
5
+ *
6
+ * const count = signal(0);
7
+ * count(); // read
8
+ * count.set(1); // write
9
+ *
10
+ * `signal` is `createSignal` with the setter attached to the accessor rather than handed
11
+ * back beside it. The returned function is the accessor itself, so a read is the call it
12
+ * always was and `count` still passes anywhere an accessor is expected. Only the write
13
+ * changes spelling. `memo` is `createMemo` renamed and no more than that: a derived value
14
+ * has nothing to set, so there is nothing to attach.
15
+ *
16
+ * The rule across the API is to read a thing the way its shape implies. A call for a
17
+ * value, a property for an object (see `store`), and `.set()` to write.
18
+ *
19
+ * The long names are unchanged and the two spellings are one primitive, so they mix
20
+ * freely. `onCleanup`, `getOwner` and `runWithOwner` are not here: they have no `create`
21
+ * to drop, and `cleanup` would read as performing one rather than registering one.
22
+ *
23
+ * Two of these names promise scheduling they do not deliver, which the per-function
24
+ * docs say outright: `renderEffect` has the same timing as `effect`, and `computed` runs
25
+ * in creation order alongside it rather than in an earlier phase.
26
+ */
27
+ import { createComputed, createEffect, createMemo, createRenderEffect, createSignal, } from './graph/compat.js';
28
+ import { createChildOwner, createContext, createRoot, } from './graph/runtime.js';
29
+ export function signal(value, options) {
30
+ const [read, write] = createSignal(value, options);
31
+ return Object.assign(read, { set: write });
32
+ }
33
+ /**
34
+ * A derived value, computed once per change and cached.
35
+ *
36
+ * Lazy and pull-based: the function does not run until something reads the memo, and
37
+ * then not again until one of its own dependencies changes. That is the difference from
38
+ * {@link computed}, which exists to do work rather than to hold a value.
39
+ *
40
+ * `prev` is the previous result, which makes an accumulator cheap without a second
41
+ * signal to hold it.
42
+ *
43
+ * @example
44
+ * ```ts
45
+ * const first = signal('Ada');
46
+ * const last = signal('Lovelace');
47
+ * const full = memo(() => `${first()} ${last()}`);
48
+ * full(); // 'Ada Lovelace', computed now
49
+ * full(); // cached, the function did not run again
50
+ * ```
51
+ *
52
+ * @example Reading the previous value:
53
+ * ```ts
54
+ * const high = memo((prev = 0) => Math.max(prev, reading()), 0);
55
+ * ```
56
+ */
57
+ export function memo(fn, value, options) {
58
+ return createMemo(fn, value, options);
59
+ }
60
+ /**
61
+ * Run `fn` now, and again whenever anything it read changes.
62
+ *
63
+ * Dependencies are collected by reading, not declared, so they are whatever the last
64
+ * run actually touched. A branch not taken subscribes to nothing, and a read behind a
65
+ * condition comes and goes with it.
66
+ *
67
+ * Eager. It runs once on creation and again as soon as a dependency is written, in the
68
+ * same task as the write. `batch` is what coalesces a group of writes into one run.
69
+ *
70
+ * Teardown goes through `onCleanup`, which runs before the next execution and once more
71
+ * on disposal. A returned function is **not** teardown: the return value is carried
72
+ * forward as the next call's `prev`, so returning a disposer silently leaks it. The
73
+ * effect is owned by the enclosing {@link root}, so disposing that disposes this.
74
+ *
75
+ * @example
76
+ * ```ts
77
+ * const query = signal('');
78
+ * effect(() => console.log('searching', query()));
79
+ * ```
80
+ *
81
+ * @example Teardown between runs, via onCleanup rather than a return:
82
+ * ```ts
83
+ * effect(() => {
84
+ * const id = setInterval(tick, delay());
85
+ * onCleanup(() => clearInterval(id));
86
+ * });
87
+ * ```
88
+ *
89
+ * @example Writing a signal an effect reads re-triggers it. Break the cycle with
90
+ * `untrack`, or make the write compare equal:
91
+ * ```ts
92
+ * effect(() => save(untrack(() => draft())));
93
+ * ```
94
+ *
95
+ * @returns Its disposer, for an effect created outside a root.
96
+ */
97
+ export function effect(fn, value,
98
+ /** `name` is what a devtools graph calls it, as for `signal` and `memo`. */
99
+ options) {
100
+ return createEffect(fn, value, options);
101
+ }
102
+ /**
103
+ * The rest of the `create` prefix, dropped.
104
+ *
105
+ * Each one calls through to the long name with the same arguments. Both spellings stay
106
+ * and mix freely; the graph does not know which was written.
107
+ *
108
+ * `onCleanup`, `getOwner` and `runWithOwner` keep their names. The rule here is losing
109
+ * a `create` that adds nothing, and none of those three has one; `cleanup` would also
110
+ * lose the sense that it registers a callback rather than performing one now.
111
+ */
112
+ /**
113
+ * An owner scope with an explicit disposer.
114
+ *
115
+ * Every signal, memo, effect and nested scope created while `fn` runs belongs to this
116
+ * one, and `dispose()` takes all of them down together. Without an owner an effect has
117
+ * nothing to tear it down, which is the usual source of a leak.
118
+ *
119
+ * A root created inside another root is attached to it, so disposal is recursive. To
120
+ * detach deliberately, create the root where no owner is current.
121
+ *
122
+ * @example
123
+ * ```ts
124
+ * const stop = root((dispose) => {
125
+ * effect(() => render(state()));
126
+ * onCleanup(() => detachListeners());
127
+ * return dispose;
128
+ * });
129
+ * stop(); // effect and cleanup both run
130
+ * ```
131
+ *
132
+ * @returns Whatever `fn` returns. Return the disposer when the caller needs it.
133
+ */
134
+ export function root(fn) {
135
+ return createRoot(fn);
136
+ }
137
+ /**
138
+ * The effect form `@fluixi/dom` wires its bindings with.
139
+ *
140
+ * Timing is identical to {@link effect} in this runtime: both are eager, and both
141
+ * re-run in the task that wrote their dependency. The render-versus-commit distinction
142
+ * the name suggests is a DOM-layer concern, not a graph one, so do not reach for this
143
+ * expecting different scheduling.
144
+ *
145
+ * What differs is that it is not reported to devtools. Every DOM binding goes through
146
+ * here, and a graph carrying one node per text node is not a graph anyone reads.
147
+ *
148
+ * @example
149
+ * ```ts
150
+ * renderEffect(() => el.setAttribute('aria-expanded', String(open())));
151
+ * ```
152
+ */
153
+ export function renderEffect(fn, value) {
154
+ return createRenderEffect(fn, value);
155
+ }
156
+ /**
157
+ * A tracked computation whose result nobody reads.
158
+ *
159
+ * Eager where {@link memo} is lazy. A memo that nothing reads never runs at all, so a
160
+ * memo written for its side effect silently does nothing; this is the form for work
161
+ * that has to happen on every change.
162
+ *
163
+ * Timing matches {@link effect}, and so does ordering: they run in creation order, not
164
+ * in two phases. A `computed` that writes a signal an effect reads has to be created
165
+ * first for the effect to see the settled value.
166
+ *
167
+ * @example
168
+ * ```ts
169
+ * computed(() => {
170
+ * valid.set(email().includes('@')); // derive into another signal
171
+ * });
172
+ * ```
173
+ *
174
+ * @example `prev` threads the last result through, with no signal to hold it:
175
+ * ```ts
176
+ * computed((runs = 0) => {
177
+ * void query();
178
+ * return runs + 1;
179
+ * }, 0);
180
+ * ```
181
+ */
182
+ export function computed(fn, value) {
183
+ createComputed(fn, value);
184
+ }
185
+ /**
186
+ * A context key: a value passed down an owner tree instead of through props.
187
+ *
188
+ * Lookup walks owners, not the DOM, so a consumer sees whatever provider encloses it
189
+ * reactively. A consumer with no provider above it gets `defaultValue`, which is why
190
+ * supplying one is usually better than handling undefined everywhere.
191
+ *
192
+ * Pass `name`. Unnamed, the key is a bare symbol and a devtools panel has nothing to
193
+ * label the node with.
194
+ *
195
+ * @example
196
+ * ```ts
197
+ * const Theme = context<'light' | 'dark'>('light', 'theme');
198
+ *
199
+ * // provider side, as a component
200
+ * Theme.Provider({ value: 'dark', children: () => renderPage() });
201
+ *
202
+ * // consumer side, anywhere below it
203
+ * const theme = useContext(Theme); // 'dark' here, 'light' with no provider
204
+ * ```
205
+ */
206
+ export function context(defaultValue, name) {
207
+ return createContext(defaultValue, name);
208
+ }
209
+ /**
210
+ * A child scope of `parent`, created without entering it.
211
+ *
212
+ * Low level, and rarely the right tool. {@link root} both creates a scope and makes it
213
+ * current, which is what almost all code wants. This hands back an owner to hold and
214
+ * enter later with `runWithOwner`, for a scope whose lifetime does not match the call
215
+ * that created it: a cached subtree, or one list row among many.
216
+ *
217
+ * Disposing `parent` disposes this, since it is attached on creation.
218
+ *
219
+ * @example
220
+ * ```ts
221
+ * const scope = childOwner(getOwner());
222
+ * // later, and possibly from another task
223
+ * runWithOwner(scope, () => effect(() => paint(row())));
224
+ * ```
225
+ */
226
+ export function childOwner(parent) {
227
+ return createChildOwner(parent);
228
+ }