flint-reactivity 4.0.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.
package/README.md ADDED
@@ -0,0 +1,107 @@
1
+ # @flint/reactivity
2
+
3
+ > Fine-grained signals system for Flint — the fastest reactive primitives
4
+
5
+ ## Install
6
+
7
+ ```bash
8
+ npm install @flint/reactivity
9
+ ```
10
+
11
+ ## Quick Start
12
+
13
+ ```typescript
14
+ import { state, computed, effect } from '@flint/reactivity'
15
+
16
+ const count = state(0)
17
+ const doubled = computed(() => count() * 2)
18
+
19
+ effect(() => {
20
+ console.log(`Count: ${count()}, Doubled: ${doubled()}`)
21
+ })
22
+
23
+ count.set(5) // Logs: Count: 5, Doubled: 10
24
+ ```
25
+
26
+ ## API
27
+
28
+ ### `state(initial)`
29
+
30
+ Create a reactive signal.
31
+
32
+ ```typescript
33
+ const count = state(0)
34
+ count() // read: 0
35
+ count.set(5) // write: 5
36
+ count.set(c => c + 1) // write: 6
37
+ count.peek() // read without tracking
38
+ ```
39
+
40
+ ### `computed(fn)`
41
+
42
+ Create a derived value (lazy, cached).
43
+
44
+ ```typescript
45
+ const doubled = computed(() => count() * 2)
46
+ doubled() // recomputes only when count() changes
47
+ ```
48
+
49
+ ### `computedSet({ get, set })`
50
+
51
+ Create a writable computed value.
52
+
53
+ ```typescript
54
+ const count = state(0)
55
+ const doubled = computedSet({
56
+ get: () => count() * 2,
57
+ set: (value) => count.set(value / 2)
58
+ })
59
+ doubled() // read: 0
60
+ doubled.set(10) // write: sets count to 5
61
+ ```
62
+
63
+ ### `effect(fn)`
64
+
65
+ Run side effects when dependencies change.
66
+
67
+ ```typescript
68
+ effect(() => {
69
+ console.log(count())
70
+ })
71
+ ```
72
+
73
+ ### `batch(fn)`
74
+
75
+ Group multiple updates into one.
76
+
77
+ ```typescript
78
+ batch(() => {
79
+ count.set(1)
80
+ name.set('hello')
81
+ }) // Only one re-render
82
+ ```
83
+
84
+ ### `reactive(obj)`
85
+
86
+ Proxy-based reactivity (like Vue).
87
+
88
+ ```typescript
89
+ const user = reactive({ name: 'John', age: 30 })
90
+ user.age++ // triggers updates
91
+ ```
92
+
93
+ ### `model(config)`
94
+
95
+ State + computed + actions in one object.
96
+
97
+ ```typescript
98
+ const counter = model({
99
+ state: { count: 0 },
100
+ computed: { doubled: (s) => s.count * 2 },
101
+ actions: { increment(s) { s.count++ } }
102
+ })
103
+ ```
104
+
105
+ ## License
106
+
107
+ MIT
@@ -0,0 +1,120 @@
1
+ import { batch, createRoot } from './signals.js';
2
+ /**
3
+ * Create a reactive signal (Solid.js-compatible alias for `state()`).
4
+ *
5
+ * @example
6
+ * // Solid style:
7
+ * const [count, setCount] = createSignal(0)
8
+ * count() // read
9
+ * setCount(1) // set
10
+ * setCount(prev => prev + 1) // update from previous
11
+ *
12
+ * // Flint style (equivalent):
13
+ * const count = state(0)
14
+ * count() // read
15
+ * count.set(1) // set
16
+ */
17
+ export declare function createSignal<T>(initialValue: T): [() => T, (value: T | ((prev: T) => T)) => void];
18
+ /**
19
+ * Create a side effect (Solid.js-compatible alias for `effect()`).
20
+ *
21
+ * @example
22
+ * createEffect(() => {
23
+ * console.log('Count changed:', count())
24
+ * })
25
+ */
26
+ export declare function createEffect(fn: () => void): void;
27
+ /**
28
+ * Create a memoized derived value (Solid.js-compatible alias for `computed()`).
29
+ *
30
+ * @example
31
+ * const doubled = createMemo(() => count() * 2)
32
+ */
33
+ export declare function createMemo<T>(fn: () => T): () => T;
34
+ /**
35
+ * Create a reactive store (Solid.js-compatible).
36
+ *
37
+ * @example
38
+ * const [store, setStore] = createStore({
39
+ * user: { name: 'John', age: 30 },
40
+ * todos: []
41
+ * })
42
+ *
43
+ * // Read
44
+ * store.user.name // 'John'
45
+ *
46
+ * // Shallow set (replaces property)
47
+ * setStore('user', 'name', 'Jane')
48
+ *
49
+ * // Functional update
50
+ * setStore('todos', todos => [...todos, { text: 'New', done: false }])
51
+ */
52
+ export declare function createStore<T extends Record<string, any>>(initialValue: T): [T, (path: string, value: any) => void];
53
+ /**
54
+ * Create a reactive root (Solid.js-compatible alias for `createRoot()`).
55
+ *
56
+ * @example
57
+ * createRoot((dispose) => {
58
+ * effect(() => console.log(count()))
59
+ * // cleanup when disposed
60
+ * return () => cleanup()
61
+ * })
62
+ */
63
+ export { createRoot };
64
+ /**
65
+ * Batch multiple updates into a single re-render (Solid.js-compatible).
66
+ *
67
+ * @example
68
+ * batch(() => {
69
+ * setCount(1)
70
+ * setName('John')
71
+ * // Only one re-render happens
72
+ * })
73
+ */
74
+ export { batch };
75
+ /**
76
+ * Create an async resource (Solid.js-compatible).
77
+ *
78
+ * @example
79
+ * const [data, { mutate, refetch }] = createResource(
80
+ * () => userId(),
81
+ * async (id) => {
82
+ * const res = await fetch(`/api/users/${id}`)
83
+ * return res.json()
84
+ * }
85
+ * )
86
+ *
87
+ * // In JSX:
88
+ * <Suspense fallback={<Loading />}>
89
+ * <div>{data()?.name}</div>
90
+ * </Suspense>
91
+ */
92
+ export declare function createResource<T, S = void>(source: (() => S) | S, fetcher: (source: S) => Promise<T>): [
93
+ () => T | undefined,
94
+ {
95
+ mutate: (fn: T | ((prev: T | undefined) => T)) => void;
96
+ refetch: () => void;
97
+ state: () => 'unresolved' | 'pending' | 'ready' | 'error' | 'refreshing';
98
+ error: () => any | undefined;
99
+ }
100
+ ];
101
+ /**
102
+ * Create a reactive value from a non-reactive source.
103
+ *
104
+ * @example
105
+ * const mouseX = from(document, 'mousemove', (e) => e.clientX)
106
+ */
107
+ export declare function from<T>(source: EventTarget | {
108
+ subscribe: (fn: (value: T) => void) => () => void;
109
+ }, eventOrSelector: string | ((event: any) => T)): () => T | undefined;
110
+ /**
111
+ * Create an immutable update helper.
112
+ *
113
+ * @example
114
+ * produce(store, draft => {
115
+ * draft.user.name = 'Jane'
116
+ * draft.todos.push({ text: 'New', done: false })
117
+ * })
118
+ */
119
+ export declare function produce<T>(store: T, recipe: (draft: T) => void): void;
120
+ //# sourceMappingURL=compat.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compat.d.ts","sourceRoot":"","sources":["../src/compat.ts"],"names":[],"mappings":"AAGA,OAAO,EAIL,KAAK,EACL,UAAU,EAEX,MAAM,cAAc,CAAA;AAIrB;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,YAAY,CAAC,CAAC,EAC5B,YAAY,EAAE,CAAC,GACd,CAAC,MAAM,CAAC,EAAE,CAAC,KAAK,EAAE,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,KAAK,IAAI,CAAC,CAWlD;AAID;;;;;;;GAOG;AACH,wBAAgB,YAAY,CAC1B,EAAE,EAAE,MAAM,IAAI,GACb,IAAI,CAEN;AAID;;;;;GAKG;AACH,wBAAgB,UAAU,CAAC,CAAC,EAC1B,EAAE,EAAE,MAAM,CAAC,GACV,MAAM,CAAC,CAET;AAID;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,WAAW,CAAC,CAAC,SAAS,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,EACvD,YAAY,EAAE,CAAC,GACd,CAAC,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,GAAG,KAAK,IAAI,CAAC,CAgBzC;AAID;;;;;;;;;GASG;AACH,OAAO,EAAE,UAAU,EAAE,CAAA;AAQrB;;;;;;;;;GASG;AACH,OAAO,EAAE,KAAK,EAAE,CAAA;AAIhB;;;;;;;;;;;;;;;;GAgBG;AACH,wBAAgB,cAAc,CAAC,CAAC,EAAE,CAAC,GAAG,IAAI,EACxC,MAAM,EAAE,CAAC,MAAM,CAAC,CAAC,GAAG,CAAC,EACrB,OAAO,EAAE,CAAC,MAAM,EAAE,CAAC,KAAK,OAAO,CAAC,CAAC,CAAC,GACjC;IACD,MAAM,CAAC,GAAG,SAAS;IACnB;QACE,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC,GAAG,SAAS,KAAK,CAAC,CAAC,KAAK,IAAI,CAAA;QACtD,OAAO,EAAE,MAAM,IAAI,CAAA;QACnB,KAAK,EAAE,MAAM,YAAY,GAAG,SAAS,GAAG,OAAO,GAAG,OAAO,GAAG,YAAY,CAAA;QACxE,KAAK,EAAE,MAAM,GAAG,GAAG,SAAS,CAAA;KAC7B;CACF,CAqDA;AAID;;;;;GAKG;AACH,wBAAgB,IAAI,CAAC,CAAC,EACpB,MAAM,EAAE,WAAW,GAAG;IAAE,SAAS,EAAE,CAAC,EAAE,EAAE,CAAC,KAAK,EAAE,CAAC,KAAK,IAAI,KAAK,MAAM,IAAI,CAAA;CAAE,EAC3E,eAAe,EAAE,MAAM,GAAG,CAAC,CAAC,KAAK,EAAE,GAAG,KAAK,CAAC,CAAC,GAC5C,MAAM,CAAC,GAAG,SAAS,CAgBrB;AAID;;;;;;;;GAQG;AACH,wBAAgB,OAAO,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,EAAE,MAAM,EAAE,CAAC,KAAK,EAAE,CAAC,KAAK,IAAI,GAAG,IAAI,CAKrE"}
package/dist/compat.js ADDED
@@ -0,0 +1,229 @@
1
+ // Flint Reactivity — Solid/React-compatible Aliases
2
+ // For developers coming from React/Solid.js backgrounds
3
+ import { state, computed, effect, batch, createRoot, reactive, } from './signals.js';
4
+ // ─── createSignal ───────────────────────────────────────────────
5
+ /**
6
+ * Create a reactive signal (Solid.js-compatible alias for `state()`).
7
+ *
8
+ * @example
9
+ * // Solid style:
10
+ * const [count, setCount] = createSignal(0)
11
+ * count() // read
12
+ * setCount(1) // set
13
+ * setCount(prev => prev + 1) // update from previous
14
+ *
15
+ * // Flint style (equivalent):
16
+ * const count = state(0)
17
+ * count() // read
18
+ * count.set(1) // set
19
+ */
20
+ export function createSignal(initialValue) {
21
+ const s = state(initialValue);
22
+ const getter = () => s();
23
+ const setter = (value) => {
24
+ if (typeof value === 'function') {
25
+ s.set(value(s()));
26
+ }
27
+ else {
28
+ s.set(value);
29
+ }
30
+ };
31
+ return [getter, setter];
32
+ }
33
+ // ─── createEffect ───────────────────────────────────────────────
34
+ /**
35
+ * Create a side effect (Solid.js-compatible alias for `effect()`).
36
+ *
37
+ * @example
38
+ * createEffect(() => {
39
+ * console.log('Count changed:', count())
40
+ * })
41
+ */
42
+ export function createEffect(fn) {
43
+ effect(fn);
44
+ }
45
+ // ─── createMemo ─────────────────────────────────────────────────
46
+ /**
47
+ * Create a memoized derived value (Solid.js-compatible alias for `computed()`).
48
+ *
49
+ * @example
50
+ * const doubled = createMemo(() => count() * 2)
51
+ */
52
+ export function createMemo(fn) {
53
+ return computed(fn);
54
+ }
55
+ // ─── createStore ────────────────────────────────────────────────
56
+ /**
57
+ * Create a reactive store (Solid.js-compatible).
58
+ *
59
+ * @example
60
+ * const [store, setStore] = createStore({
61
+ * user: { name: 'John', age: 30 },
62
+ * todos: []
63
+ * })
64
+ *
65
+ * // Read
66
+ * store.user.name // 'John'
67
+ *
68
+ * // Shallow set (replaces property)
69
+ * setStore('user', 'name', 'Jane')
70
+ *
71
+ * // Functional update
72
+ * setStore('todos', todos => [...todos, { text: 'New', done: false }])
73
+ */
74
+ export function createStore(initialValue) {
75
+ const store = reactive(initialValue);
76
+ const setStore = (path, value) => {
77
+ const keys = path.split('.');
78
+ let current = store;
79
+ for (let i = 0; i < keys.length - 1; i++) {
80
+ current = current[keys[i]];
81
+ }
82
+ const lastKey = keys[keys.length - 1];
83
+ if (typeof value === 'function') {
84
+ current[lastKey] = value(current[lastKey]);
85
+ }
86
+ else {
87
+ current[lastKey] = value;
88
+ }
89
+ };
90
+ return [store, setStore];
91
+ }
92
+ // ─── createRoot (Solid-compatible) ──────────────────────────────
93
+ /**
94
+ * Create a reactive root (Solid.js-compatible alias for `createRoot()`).
95
+ *
96
+ * @example
97
+ * createRoot((dispose) => {
98
+ * effect(() => console.log(count()))
99
+ * // cleanup when disposed
100
+ * return () => cleanup()
101
+ * })
102
+ */
103
+ export { createRoot };
104
+ // ─── createSelector ─────────────────────────────────────────────
105
+ // Note: createSelector is already exported from signals.ts with the full API
106
+ // (setSelected, getSelected, dispose). We re-export it here for compatibility.
107
+ // ─── batch (Solid-compatible) ───────────────────────────────────
108
+ /**
109
+ * Batch multiple updates into a single re-render (Solid.js-compatible).
110
+ *
111
+ * @example
112
+ * batch(() => {
113
+ * setCount(1)
114
+ * setName('John')
115
+ * // Only one re-render happens
116
+ * })
117
+ */
118
+ export { batch };
119
+ // ─── createResource ─────────────────────────────────────────────
120
+ /**
121
+ * Create an async resource (Solid.js-compatible).
122
+ *
123
+ * @example
124
+ * const [data, { mutate, refetch }] = createResource(
125
+ * () => userId(),
126
+ * async (id) => {
127
+ * const res = await fetch(`/api/users/${id}`)
128
+ * return res.json()
129
+ * }
130
+ * )
131
+ *
132
+ * // In JSX:
133
+ * <Suspense fallback={<Loading />}>
134
+ * <div>{data()?.name}</div>
135
+ * </Suspense>
136
+ */
137
+ export function createResource(source, fetcher) {
138
+ const dataSignal = state(undefined);
139
+ const errorSignal = state(undefined);
140
+ const stateSignal = state('unresolved');
141
+ let fetchCount = 0;
142
+ const refetch = () => {
143
+ fetchCount++;
144
+ const currentFetch = fetchCount;
145
+ const src = typeof source === 'function' ? source() : source;
146
+ stateSignal.set('pending');
147
+ fetcher(src)
148
+ .then((result) => {
149
+ if (currentFetch === fetchCount) {
150
+ dataSignal.set(result);
151
+ stateSignal.set('ready');
152
+ }
153
+ })
154
+ .catch((err) => {
155
+ if (currentFetch === fetchCount) {
156
+ errorSignal.set(err);
157
+ stateSignal.set('error');
158
+ }
159
+ });
160
+ };
161
+ // Start fetching immediately if source is available
162
+ if (typeof source === 'function') {
163
+ effect(() => {
164
+ const src = source();
165
+ if (src !== undefined && src !== null) {
166
+ refetch();
167
+ }
168
+ });
169
+ }
170
+ else {
171
+ refetch();
172
+ }
173
+ return [
174
+ () => dataSignal(),
175
+ {
176
+ mutate: (fn) => {
177
+ if (typeof fn === 'function') {
178
+ dataSignal.set(fn);
179
+ }
180
+ else {
181
+ dataSignal.set(fn);
182
+ }
183
+ },
184
+ refetch,
185
+ state: () => stateSignal(),
186
+ error: () => errorSignal(),
187
+ },
188
+ ];
189
+ }
190
+ // ─── from (reactive from) ───────────────────────────────────────
191
+ /**
192
+ * Create a reactive value from a non-reactive source.
193
+ *
194
+ * @example
195
+ * const mouseX = from(document, 'mousemove', (e) => e.clientX)
196
+ */
197
+ export function from(source, eventOrSelector) {
198
+ const signal = state(undefined);
199
+ if ('addEventListener' in source) {
200
+ const eventName = eventOrSelector;
201
+ const selector = typeof eventOrSelector === 'function' ? eventOrSelector : (e) => e;
202
+ source.addEventListener(eventName, (e) => {
203
+ signal.set(selector(e));
204
+ });
205
+ }
206
+ else {
207
+ source.subscribe((value) => {
208
+ signal.set(value);
209
+ });
210
+ }
211
+ return () => signal();
212
+ }
213
+ // ─── produce (immutable helper) ─────────────────────────────────
214
+ /**
215
+ * Create an immutable update helper.
216
+ *
217
+ * @example
218
+ * produce(store, draft => {
219
+ * draft.user.name = 'Jane'
220
+ * draft.todos.push({ text: 'New', done: false })
221
+ * })
222
+ */
223
+ export function produce(store, recipe) {
224
+ // Simple immutable update pattern
225
+ if (typeof store === 'object' && store !== null) {
226
+ recipe(store);
227
+ }
228
+ }
229
+ //# sourceMappingURL=compat.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"compat.js","sourceRoot":"","sources":["../src/compat.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,130 @@
1
+ import type { Signal, Computed } from './types.js';
2
+ export interface DebugOptions {
3
+ /** Enable debug mode */
4
+ enabled: boolean;
5
+ /** Log signal changes */
6
+ logChanges: boolean;
7
+ /** Log computed recalculations */
8
+ logComputed: boolean;
9
+ /** Log effect executions */
10
+ logEffects: boolean;
11
+ /** Log batch operations */
12
+ logBatch: boolean;
13
+ /** Maximum history entries per signal */
14
+ maxHistory: number;
15
+ /** Enable performance tracking */
16
+ trackPerformance: boolean;
17
+ }
18
+ export interface SignalDebugInfo {
19
+ id: string;
20
+ name: string;
21
+ value: any;
22
+ previousValue: any;
23
+ changeCount: number;
24
+ lastChange: number;
25
+ history: SignalHistoryEntry[];
26
+ subscribers: string[];
27
+ computedFrom: string[];
28
+ }
29
+ export interface SignalHistoryEntry {
30
+ value: any;
31
+ timestamp: number;
32
+ stackTrace?: string;
33
+ }
34
+ export interface ComputedDebugInfo {
35
+ id: string;
36
+ name: string;
37
+ value: any;
38
+ recalculationCount: number;
39
+ lastRecalculation: number;
40
+ dependencies: string[];
41
+ isDirty: boolean;
42
+ computationTime: number;
43
+ }
44
+ export interface EffectDebugInfo {
45
+ id: string;
46
+ name: string;
47
+ executionCount: number;
48
+ lastExecution: number;
49
+ dependencies: string[];
50
+ executionTime: number;
51
+ }
52
+ export declare class DebugManager {
53
+ private options;
54
+ private signalRegistry;
55
+ private computedRegistry;
56
+ private effectRegistry;
57
+ private idCounter;
58
+ private enabled;
59
+ constructor(options?: Partial<DebugOptions>);
60
+ /**
61
+ * Enable debug mode
62
+ */
63
+ enable(): void;
64
+ /**
65
+ * Disable debug mode
66
+ */
67
+ disable(): void;
68
+ /**
69
+ * Track a signal
70
+ */
71
+ trackSignal<T>(name: string, signal: Signal<T>): Signal<T>;
72
+ /**
73
+ * Track a computed value
74
+ */
75
+ trackComputed<T>(name: string, computed$: Computed<T>): Computed<T>;
76
+ /**
77
+ * Get debug info for a signal
78
+ */
79
+ getSignalDebugInfo(id: string): SignalDebugInfo | undefined;
80
+ /**
81
+ * Get debug info for a computed
82
+ */
83
+ getComputedDebugInfo(id: string): ComputedDebugInfo | undefined;
84
+ /**
85
+ * Get all tracked signals
86
+ */
87
+ getAllSignals(): SignalDebugInfo[];
88
+ /**
89
+ * Get all tracked computed values
90
+ */
91
+ getAllComputed(): ComputedDebugInfo[];
92
+ /**
93
+ * Clear all tracking data
94
+ */
95
+ clear(): void;
96
+ /**
97
+ * Get performance summary
98
+ */
99
+ getPerformanceSummary(): {
100
+ totalSignals: number;
101
+ totalComputed: number;
102
+ totalEffects: number;
103
+ averageComputationTime: number;
104
+ };
105
+ }
106
+ export declare function createDebugManager(options?: Partial<DebugOptions>): DebugManager;
107
+ export declare function getDebugManager(): DebugManager | null;
108
+ export declare function enableDebug(): DebugManager;
109
+ export declare function disableDebug(): void;
110
+ /**
111
+ * Track a signal in debug mode
112
+ */
113
+ export declare function trackSignal<T>(name: string, signal: Signal<T>): Signal<T>;
114
+ /**
115
+ * Track a computed in debug mode
116
+ */
117
+ export declare function trackComputed<T>(name: string, computed$: Computed<T>): Computed<T>;
118
+ /**
119
+ * Print signal history
120
+ */
121
+ export declare function printSignalHistory(signalId: string): void;
122
+ /**
123
+ * Print computed stats
124
+ */
125
+ export declare function printComputedStats(computedId: string): void;
126
+ /**
127
+ * Print performance summary
128
+ */
129
+ export declare function printPerformanceSummary(): void;
130
+ //# sourceMappingURL=debug.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"debug.d.ts","sourceRoot":"","sources":["../src/debug.ts"],"names":[],"mappings":"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"}