@quazardous/quarkernel 1.0.11 → 2.2.2
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 +57 -51
- package/dist/create-machine-CYsscHPX.d.cts +275 -0
- package/dist/create-machine-CYsscHPX.d.ts +275 -0
- package/dist/fsm.cjs +1436 -0
- package/dist/fsm.cjs.map +1 -0
- package/dist/fsm.d.cts +2 -0
- package/dist/fsm.d.ts +2 -0
- package/dist/fsm.js +1432 -0
- package/dist/fsm.js.map +1 -0
- package/dist/index-BDf1xZi6.d.cts +896 -0
- package/dist/index-BPMXiW32.d.ts +896 -0
- package/dist/index.cjs +1750 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +80 -0
- package/dist/index.d.ts +80 -0
- package/dist/index.js +1722 -0
- package/dist/index.js.map +1 -0
- package/dist/xstate.cjs +190 -0
- package/dist/xstate.cjs.map +1 -0
- package/dist/xstate.d.cts +152 -0
- package/dist/xstate.d.ts +152 -0
- package/dist/xstate.js +186 -0
- package/dist/xstate.js.map +1 -0
- package/package.json +62 -24
- package/LICENSE +0 -21
- package/src/index.js +0 -3
- package/src/lib/QuarKernel.js +0 -390
- package/types/QuarKernel.d.ts +0 -122
|
@@ -0,0 +1,896 @@
|
|
|
1
|
+
import { M as MachineConfig, a as Machine } from './create-machine-CYsscHPX.cjs';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* KernelEvent - Custom event implementation for QuarKernel
|
|
5
|
+
*
|
|
6
|
+
* NOT based on native Event/EventTarget for design reasons:
|
|
7
|
+
* - Need shared mutable context between listeners
|
|
8
|
+
* - Need dependency-ordered execution
|
|
9
|
+
* - Simpler API without DOM baggage
|
|
10
|
+
*/
|
|
11
|
+
/**
|
|
12
|
+
* Event propagation control for listener execution
|
|
13
|
+
*/
|
|
14
|
+
declare class KernelEvent<T = unknown> {
|
|
15
|
+
/**
|
|
16
|
+
* Event name/type
|
|
17
|
+
*/
|
|
18
|
+
readonly name: string;
|
|
19
|
+
/**
|
|
20
|
+
* Event payload (typed, immutable)
|
|
21
|
+
*/
|
|
22
|
+
readonly data: T;
|
|
23
|
+
/**
|
|
24
|
+
* Shared mutable context for passing data between listeners
|
|
25
|
+
*/
|
|
26
|
+
readonly context: Record<string, any>;
|
|
27
|
+
/**
|
|
28
|
+
* Event creation timestamp (milliseconds since epoch)
|
|
29
|
+
*/
|
|
30
|
+
readonly timestamp: number;
|
|
31
|
+
/**
|
|
32
|
+
* Internal flag: stop propagation to remaining listeners
|
|
33
|
+
* @private
|
|
34
|
+
*/
|
|
35
|
+
private _propagationStopped;
|
|
36
|
+
constructor(name: string, data: T, context?: Record<string, any>);
|
|
37
|
+
/**
|
|
38
|
+
* Stop propagation to remaining listeners in the chain
|
|
39
|
+
* Similar to DOM Event.stopPropagation()
|
|
40
|
+
*
|
|
41
|
+
* After calling this, no more listeners will execute.
|
|
42
|
+
*/
|
|
43
|
+
stopPropagation: () => void;
|
|
44
|
+
/**
|
|
45
|
+
* Check if propagation was stopped
|
|
46
|
+
* @internal
|
|
47
|
+
*/
|
|
48
|
+
get isPropagationStopped(): boolean;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
/**
|
|
52
|
+
* ListenerContext provides metadata and utilities for event listeners.
|
|
53
|
+
* Passed as the second parameter to listener callbacks: (event, ctx) => {}
|
|
54
|
+
*
|
|
55
|
+
* Features:
|
|
56
|
+
* - Listener metadata (id, eventName, priority, dependencies)
|
|
57
|
+
* - Cancellation via cancel() or AbortSignal
|
|
58
|
+
* - Event emission from within listeners
|
|
59
|
+
* - Propagation control
|
|
60
|
+
*/
|
|
61
|
+
|
|
62
|
+
/**
|
|
63
|
+
* Context object passed to each listener callback.
|
|
64
|
+
* Provides utilities for listener self-management without polluting the event object.
|
|
65
|
+
*/
|
|
66
|
+
declare class ListenerContext {
|
|
67
|
+
/** Unique identifier for this listener instance */
|
|
68
|
+
readonly id: string;
|
|
69
|
+
/** Event name this listener is registered for */
|
|
70
|
+
readonly eventName: string;
|
|
71
|
+
/** Listener priority (higher = earlier execution) */
|
|
72
|
+
readonly priority: number;
|
|
73
|
+
/** Listener dependencies (IDs of listeners that must execute first) */
|
|
74
|
+
readonly dependencies: readonly string[];
|
|
75
|
+
/** AbortSignal for cancellation (if provided during registration) */
|
|
76
|
+
readonly signal?: AbortSignal;
|
|
77
|
+
/** Reference to the kernel instance for emit/off operations */
|
|
78
|
+
private readonly kernel;
|
|
79
|
+
/** Reference to the listener function for removal */
|
|
80
|
+
private readonly listenerFn;
|
|
81
|
+
/** Current event being processed (set during emit) */
|
|
82
|
+
private currentEvent?;
|
|
83
|
+
/**
|
|
84
|
+
* Creates a new ListenerContext.
|
|
85
|
+
* @internal Use Kernel.on() to register listeners, which creates contexts automatically.
|
|
86
|
+
*/
|
|
87
|
+
constructor(id: string, eventName: string, priority: number, dependencies: readonly string[], kernel: ListenerContextKernel, listenerFn: Function, signal?: AbortSignal);
|
|
88
|
+
/**
|
|
89
|
+
* Sets the current event being processed.
|
|
90
|
+
* @internal Called by Kernel during emit()
|
|
91
|
+
*/
|
|
92
|
+
setCurrentEvent: (event: KernelEvent<any>) => void;
|
|
93
|
+
/**
|
|
94
|
+
* Clears the current event after processing.
|
|
95
|
+
* @internal Called by Kernel after listener execution
|
|
96
|
+
*/
|
|
97
|
+
clearCurrentEvent: () => void;
|
|
98
|
+
/**
|
|
99
|
+
* Removes this listener from the kernel.
|
|
100
|
+
* Alias for kernel.off() with this listener's reference.
|
|
101
|
+
*/
|
|
102
|
+
cancel: () => void;
|
|
103
|
+
/**
|
|
104
|
+
* Alias for cancel() to match common naming patterns.
|
|
105
|
+
*/
|
|
106
|
+
off: () => void;
|
|
107
|
+
/**
|
|
108
|
+
* Emits an event from within this listener.
|
|
109
|
+
* Delegates to kernel.emit().
|
|
110
|
+
*/
|
|
111
|
+
emit: <T = any>(eventName: string, data?: T) => Promise<void>;
|
|
112
|
+
/**
|
|
113
|
+
* Stops propagation of the current event to remaining listeners.
|
|
114
|
+
* Requires an event to be currently processing.
|
|
115
|
+
*/
|
|
116
|
+
stopPropagation: () => void;
|
|
117
|
+
}
|
|
118
|
+
/**
|
|
119
|
+
* Minimal kernel interface required by ListenerContext.
|
|
120
|
+
* Prevents circular dependencies between ListenerContext and Kernel.
|
|
121
|
+
*/
|
|
122
|
+
interface ListenerContextKernel {
|
|
123
|
+
off(eventName: string, listener: Function): void;
|
|
124
|
+
emit<T = any>(eventName: string, data?: T): Promise<void>;
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
/**
|
|
128
|
+
* Composition types for QuarKernel v2
|
|
129
|
+
*
|
|
130
|
+
* Types for composite events, context merging strategies, and conflict detection.
|
|
131
|
+
*/
|
|
132
|
+
/**
|
|
133
|
+
* Name of a source event in a composition
|
|
134
|
+
*
|
|
135
|
+
* When composing events like `compose(['user:loaded', 'profile:loaded'], 'app:ready')`,
|
|
136
|
+
* the event names 'user:loaded' and 'profile:loaded' are used as keys to merge their contexts.
|
|
137
|
+
*/
|
|
138
|
+
type EventName$1 = string;
|
|
139
|
+
/**
|
|
140
|
+
* Result of a context merge operation
|
|
141
|
+
*/
|
|
142
|
+
interface MergeResult {
|
|
143
|
+
/** The merged context object */
|
|
144
|
+
context: Record<string, any>;
|
|
145
|
+
/** Array of detected conflicts during merge */
|
|
146
|
+
conflicts: ConflictInfo[];
|
|
147
|
+
}
|
|
148
|
+
/**
|
|
149
|
+
* Context merger strategy interface
|
|
150
|
+
*
|
|
151
|
+
* Implementations define how to merge contexts from multiple source events
|
|
152
|
+
* when creating a composite event.
|
|
153
|
+
*/
|
|
154
|
+
interface ContextMerger$1 {
|
|
155
|
+
/**
|
|
156
|
+
* Merge contexts from multiple source events
|
|
157
|
+
*
|
|
158
|
+
* @param contexts - Map of source event names to their event context objects
|
|
159
|
+
* @param sources - Array of source event names in order of emission
|
|
160
|
+
* @returns Merged context object for the composite event
|
|
161
|
+
*/
|
|
162
|
+
merge(contexts: Map<EventName$1, Record<string, any>>, sources: EventName$1[]): Record<string, any>;
|
|
163
|
+
/**
|
|
164
|
+
* Merge contexts and detect conflicts
|
|
165
|
+
*
|
|
166
|
+
* @param contexts - Map of source event names to their event context objects
|
|
167
|
+
* @param sources - Array of source event names in order of emission
|
|
168
|
+
* @returns MergeResult with merged context and detected conflicts
|
|
169
|
+
*/
|
|
170
|
+
mergeWithConflicts(contexts: Map<EventName$1, Record<string, any>>, sources: EventName$1[]): MergeResult;
|
|
171
|
+
}
|
|
172
|
+
/**
|
|
173
|
+
* Information about a context key conflict during merge
|
|
174
|
+
*/
|
|
175
|
+
interface ConflictInfo {
|
|
176
|
+
/** The context key that has conflicting values */
|
|
177
|
+
key: string;
|
|
178
|
+
/** Source event names that provided values for this key */
|
|
179
|
+
sources: EventName$1[];
|
|
180
|
+
/** The actual values from each source (in same order as sources) */
|
|
181
|
+
values: any[];
|
|
182
|
+
}
|
|
183
|
+
/**
|
|
184
|
+
* Options for creating a composition
|
|
185
|
+
*/
|
|
186
|
+
interface CompositionOptions$1 {
|
|
187
|
+
/**
|
|
188
|
+
* Context merger strategy to use
|
|
189
|
+
* @default NamespacedMerger
|
|
190
|
+
*/
|
|
191
|
+
merger?: ContextMerger$1;
|
|
192
|
+
/**
|
|
193
|
+
* Maximum number of events to buffer per source event
|
|
194
|
+
* @default 100
|
|
195
|
+
*/
|
|
196
|
+
bufferLimit?: number;
|
|
197
|
+
/**
|
|
198
|
+
* Whether to reset the buffer after emitting composite event
|
|
199
|
+
* @default true
|
|
200
|
+
*/
|
|
201
|
+
reset?: boolean;
|
|
202
|
+
/**
|
|
203
|
+
* Callback for context conflicts (debug mode)
|
|
204
|
+
*/
|
|
205
|
+
onConflict?: (conflict: ConflictInfo) => void;
|
|
206
|
+
/**
|
|
207
|
+
* Global time-to-live for buffered events in milliseconds.
|
|
208
|
+
* Events older than this will be considered expired and won't count
|
|
209
|
+
* toward composition readiness.
|
|
210
|
+
*
|
|
211
|
+
* @default 0 (no expiration - events stay in buffer indefinitely)
|
|
212
|
+
*
|
|
213
|
+
* @example
|
|
214
|
+
* ```ts
|
|
215
|
+
* // All events expire after 5 seconds
|
|
216
|
+
* const composition = new Composition(kernels, { eventTTL: 5000 });
|
|
217
|
+
* ```
|
|
218
|
+
*/
|
|
219
|
+
eventTTL?: number;
|
|
220
|
+
/**
|
|
221
|
+
* Per-event TTL configuration. Overrides global eventTTL for specific events.
|
|
222
|
+
*
|
|
223
|
+
* Values can be:
|
|
224
|
+
* - `0` or `'permanent'`: Event stays in buffer indefinitely (default)
|
|
225
|
+
* - `number > 0`: Event expires after N milliseconds
|
|
226
|
+
* - `'instant'`: Event only triggers if it completes a composition immediately,
|
|
227
|
+
* otherwise it's discarded (doesn't wait in buffer)
|
|
228
|
+
*
|
|
229
|
+
* @example
|
|
230
|
+
* ```ts
|
|
231
|
+
* const composition = new Composition(kernels, {
|
|
232
|
+
* eventTTLs: {
|
|
233
|
+
* 'user:click': 'permanent', // Waits indefinitely
|
|
234
|
+
* 'mouse:move': 100, // Expires after 100ms
|
|
235
|
+
* 'key:press': 'instant' // Must complete composition now or discard
|
|
236
|
+
* }
|
|
237
|
+
* });
|
|
238
|
+
* ```
|
|
239
|
+
*/
|
|
240
|
+
eventTTLs?: Record<EventName$1, number | 'permanent' | 'instant'>;
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
/**
|
|
244
|
+
* Type definitions for QuarKernel v2
|
|
245
|
+
*
|
|
246
|
+
* This module contains all TypeScript types, interfaces, and type guards
|
|
247
|
+
* for the event kernel. Uses strict typing with generic parameters for
|
|
248
|
+
* type-safe event handling.
|
|
249
|
+
*/
|
|
250
|
+
/**
|
|
251
|
+
* Event name type - can be string or branded type
|
|
252
|
+
*/
|
|
253
|
+
type EventName = string;
|
|
254
|
+
/**
|
|
255
|
+
* Event data type - the payload for each event
|
|
256
|
+
* Can be any JSON-serializable value or undefined
|
|
257
|
+
*/
|
|
258
|
+
type EventData = any;
|
|
259
|
+
/**
|
|
260
|
+
* Type map for events - maps event names to their data types
|
|
261
|
+
* @example
|
|
262
|
+
* ```ts
|
|
263
|
+
* interface Events {
|
|
264
|
+
* 'user:login': { userId: string }
|
|
265
|
+
* 'user:logout': { userId: string }
|
|
266
|
+
* 'app:ready': undefined
|
|
267
|
+
* }
|
|
268
|
+
* ```
|
|
269
|
+
*/
|
|
270
|
+
type EventMap = Record<EventName, EventData>;
|
|
271
|
+
/**
|
|
272
|
+
* Event object passed to listeners
|
|
273
|
+
* @template T - The event data type
|
|
274
|
+
*
|
|
275
|
+
* Note: The actual implementation is in kernel-event.ts
|
|
276
|
+
* This interface is for type checking only
|
|
277
|
+
*/
|
|
278
|
+
interface IKernelEvent<T = any> {
|
|
279
|
+
/** Event name */
|
|
280
|
+
readonly name: string;
|
|
281
|
+
/** Event payload (typed, immutable) */
|
|
282
|
+
readonly data: T;
|
|
283
|
+
/** Shared mutable context - passed through listener chain */
|
|
284
|
+
readonly context: Record<string, any>;
|
|
285
|
+
/** Timestamp when event was created */
|
|
286
|
+
readonly timestamp: number;
|
|
287
|
+
/** Stop propagation to remaining listeners */
|
|
288
|
+
stopPropagation(): void;
|
|
289
|
+
/** Whether propagation was stopped */
|
|
290
|
+
readonly isPropagationStopped: boolean;
|
|
291
|
+
}
|
|
292
|
+
/**
|
|
293
|
+
* Listener context - utilities available to each listener
|
|
294
|
+
*/
|
|
295
|
+
interface IListenerContext {
|
|
296
|
+
/** Unique identifier of this listener */
|
|
297
|
+
id: string;
|
|
298
|
+
/** Remove this listener */
|
|
299
|
+
off(): void;
|
|
300
|
+
/** Emit another event */
|
|
301
|
+
emit<K extends string = string>(event: K, data?: any): Promise<void>;
|
|
302
|
+
/** Stop propagation to remaining listeners */
|
|
303
|
+
stopPropagation(): void;
|
|
304
|
+
}
|
|
305
|
+
/**
|
|
306
|
+
* Listener function signature
|
|
307
|
+
* @template T - The event data type
|
|
308
|
+
*/
|
|
309
|
+
type ListenerFunction<T = any> = (event: IKernelEvent<T>, context: IListenerContext) => void | Promise<void>;
|
|
310
|
+
/**
|
|
311
|
+
* Predicate function for conditional once listeners
|
|
312
|
+
*
|
|
313
|
+
* IMPORTANT: Evaluated AFTER listener execution, not before.
|
|
314
|
+
* The event parameter contains the final state after the listener has run.
|
|
315
|
+
*
|
|
316
|
+
* @template T - The event data type
|
|
317
|
+
* @param event - Event with post-execution state (includes listener modifications to context)
|
|
318
|
+
* @returns true to remove the listener, false to keep it for next emission
|
|
319
|
+
*/
|
|
320
|
+
type PredicateFunction<T = any> = (event: IKernelEvent<T>) => boolean;
|
|
321
|
+
/**
|
|
322
|
+
* Options for registering a listener
|
|
323
|
+
*/
|
|
324
|
+
interface ListenerOptions {
|
|
325
|
+
/** Unique identifier for dependency resolution */
|
|
326
|
+
id?: string;
|
|
327
|
+
/** Dependencies - listener IDs that must execute before this one */
|
|
328
|
+
after?: string | string[];
|
|
329
|
+
/** Priority - higher values execute earlier (within same dependency level) */
|
|
330
|
+
priority?: number;
|
|
331
|
+
/**
|
|
332
|
+
* Listen only once - true for always, or predicate function for conditional removal
|
|
333
|
+
*
|
|
334
|
+
* IMPORTANT: The predicate is evaluated AFTER listener execution, not before.
|
|
335
|
+
* This means:
|
|
336
|
+
* - The listener always executes at least once
|
|
337
|
+
* - The predicate receives the event object after the listener has run
|
|
338
|
+
* - The predicate sees any modifications to event.context made by the listener
|
|
339
|
+
* - If the listener throws an error, the predicate still evaluates (with errorBoundary: true)
|
|
340
|
+
* - The listener is removed after execution if predicate returns true
|
|
341
|
+
*
|
|
342
|
+
* @example
|
|
343
|
+
* ```ts
|
|
344
|
+
* // Listener always executes, then removed after execution
|
|
345
|
+
* kernel.on('event', handler, { once: true });
|
|
346
|
+
*
|
|
347
|
+
* // Listener executes each time, removed after count reaches 3
|
|
348
|
+
* kernel.on('event', handler, {
|
|
349
|
+
* once: (event) => event.context.count >= 3
|
|
350
|
+
* });
|
|
351
|
+
* ```
|
|
352
|
+
*/
|
|
353
|
+
once?: boolean | PredicateFunction;
|
|
354
|
+
/** AbortSignal for cleanup */
|
|
355
|
+
signal?: AbortSignal;
|
|
356
|
+
}
|
|
357
|
+
/**
|
|
358
|
+
* Internal listener entry stored in the kernel
|
|
359
|
+
* @internal
|
|
360
|
+
*/
|
|
361
|
+
interface ListenerEntry {
|
|
362
|
+
/** Unique identifier */
|
|
363
|
+
id: string;
|
|
364
|
+
/** The listener function */
|
|
365
|
+
callback: ListenerFunction;
|
|
366
|
+
/** Dependencies (listener IDs) */
|
|
367
|
+
after: string[];
|
|
368
|
+
/** Priority for ordering */
|
|
369
|
+
priority: number;
|
|
370
|
+
/** Listen only once - true for always, or predicate function evaluated after execution */
|
|
371
|
+
once: boolean | PredicateFunction;
|
|
372
|
+
/** Original listener function reference (for off()) */
|
|
373
|
+
original: ListenerFunction;
|
|
374
|
+
/** AbortSignal for cleanup */
|
|
375
|
+
signal?: AbortSignal;
|
|
376
|
+
/** Abort event listener reference for cleanup */
|
|
377
|
+
abortListener?: () => void;
|
|
378
|
+
}
|
|
379
|
+
/**
|
|
380
|
+
* Options for creating a kernel instance
|
|
381
|
+
*/
|
|
382
|
+
interface KernelOptions {
|
|
383
|
+
/** Event name delimiter for namespacing (default: ':') */
|
|
384
|
+
delimiter?: string;
|
|
385
|
+
/** Enable wildcard pattern matching (default: true) */
|
|
386
|
+
wildcard?: boolean;
|
|
387
|
+
/** Maximum listeners per event (default: Infinity, 0 = unlimited) */
|
|
388
|
+
maxListeners?: number;
|
|
389
|
+
/** Error handler for listener exceptions */
|
|
390
|
+
onError?: (error: Error, event: IKernelEvent) => void;
|
|
391
|
+
/** Debug mode - enables warnings and logging */
|
|
392
|
+
debug?: boolean;
|
|
393
|
+
/** Error boundary - continue executing listeners even if one fails */
|
|
394
|
+
errorBoundary?: boolean;
|
|
395
|
+
/** Default context merger for composite events */
|
|
396
|
+
contextMerger?: ContextMerger | ContextMergerFunction;
|
|
397
|
+
/** Callback when context keys conflict during merge */
|
|
398
|
+
onContextConflict?: (key: string, values: any[]) => void;
|
|
399
|
+
}
|
|
400
|
+
/**
|
|
401
|
+
* Event stack for composition - maps event names to their event objects
|
|
402
|
+
*/
|
|
403
|
+
type EventStack = Record<string, IKernelEvent>;
|
|
404
|
+
/**
|
|
405
|
+
* Factory function to create composite event from source events
|
|
406
|
+
* @param stack - Map of event names to their event objects
|
|
407
|
+
* @returns The composite event specification (type and data)
|
|
408
|
+
*/
|
|
409
|
+
type CompositionFactory = (stack: EventStack) => {
|
|
410
|
+
type: string;
|
|
411
|
+
data: any;
|
|
412
|
+
} | null;
|
|
413
|
+
/**
|
|
414
|
+
* Options for event composition
|
|
415
|
+
*/
|
|
416
|
+
interface CompositionOptions {
|
|
417
|
+
/** Reset buffer after composition fires (default: true) */
|
|
418
|
+
reset?: boolean;
|
|
419
|
+
/** Context merger for this composition (overrides kernel default) */
|
|
420
|
+
contextMerger?: ContextMerger | ContextMergerFunction;
|
|
421
|
+
}
|
|
422
|
+
/**
|
|
423
|
+
* Internal composition entry
|
|
424
|
+
* @internal
|
|
425
|
+
*/
|
|
426
|
+
interface IComposition {
|
|
427
|
+
/** Event names to compose */
|
|
428
|
+
events: string[];
|
|
429
|
+
/** Buffer of received events */
|
|
430
|
+
buffer: Map<string, IKernelEvent>;
|
|
431
|
+
/** Factory to create composite event */
|
|
432
|
+
factory: CompositionFactory;
|
|
433
|
+
/** Reset buffer after firing */
|
|
434
|
+
reset: boolean;
|
|
435
|
+
/** Context merger */
|
|
436
|
+
merger: ContextMerger;
|
|
437
|
+
}
|
|
438
|
+
/**
|
|
439
|
+
* Strategy pattern for merging event contexts in compositions
|
|
440
|
+
*/
|
|
441
|
+
interface ContextMerger {
|
|
442
|
+
/**
|
|
443
|
+
* Merge contexts from multiple events
|
|
444
|
+
* @param contexts - Map of event names to their context objects
|
|
445
|
+
* @returns The merged context
|
|
446
|
+
*/
|
|
447
|
+
merge(contexts: Record<string, any>): any;
|
|
448
|
+
}
|
|
449
|
+
/**
|
|
450
|
+
* Function-based context merger (shorthand for ContextMerger interface)
|
|
451
|
+
*/
|
|
452
|
+
type ContextMergerFunction = (contexts: Record<string, any>) => any;
|
|
453
|
+
/**
|
|
454
|
+
* Main kernel interface
|
|
455
|
+
* @template Events - Event map defining event names and their data types
|
|
456
|
+
*/
|
|
457
|
+
interface IKernel<Events extends EventMap = EventMap> {
|
|
458
|
+
on<K extends keyof Events>(event: K | K[], listener: ListenerFunction<Events[K]>, options?: ListenerOptions): () => void;
|
|
459
|
+
once<K extends keyof Events>(event: K, listener: ListenerFunction<Events[K]>, options?: Omit<ListenerOptions, 'once'>): () => void;
|
|
460
|
+
once<K extends keyof Events>(event: K, predicate: PredicateFunction<Events[K]>, listener: ListenerFunction<Events[K]>, options?: Omit<ListenerOptions, 'once'>): () => void;
|
|
461
|
+
once<K extends keyof Events>(event: K): Promise<IKernelEvent<Events[K]>>;
|
|
462
|
+
off<K extends keyof Events>(event: K, listener?: ListenerFunction<Events[K]>): void;
|
|
463
|
+
offAll(event?: keyof Events): void;
|
|
464
|
+
emit<K extends keyof Events>(event: K, data?: Events[K]): Promise<void>;
|
|
465
|
+
emitSerial<K extends keyof Events>(event: K, data?: Events[K]): Promise<void>;
|
|
466
|
+
compose(events: string[], factory: CompositionFactory, options?: CompositionOptions): () => void;
|
|
467
|
+
events<K extends keyof Events>(event: K): AsyncIterable<IKernelEvent<Events[K]>>;
|
|
468
|
+
listenerCount(event?: keyof Events): number;
|
|
469
|
+
eventNames(): (keyof Events)[];
|
|
470
|
+
debug(enabled: boolean): void;
|
|
471
|
+
}
|
|
472
|
+
/**
|
|
473
|
+
* Type guard to check if value is a valid event name
|
|
474
|
+
*/
|
|
475
|
+
declare function isEventName(value: unknown): value is EventName;
|
|
476
|
+
/**
|
|
477
|
+
* Type guard to check if value is a listener function
|
|
478
|
+
*/
|
|
479
|
+
declare function isListenerFunction(value: unknown): value is ListenerFunction;
|
|
480
|
+
/**
|
|
481
|
+
* Type guard to check if value is a predicate function
|
|
482
|
+
*/
|
|
483
|
+
declare function isPredicateFunction(value: unknown): value is PredicateFunction;
|
|
484
|
+
/**
|
|
485
|
+
* Type guard to check if value is a context merger
|
|
486
|
+
*/
|
|
487
|
+
declare function isContextMerger(value: unknown): value is ContextMerger;
|
|
488
|
+
/**
|
|
489
|
+
* Type guard to check if value is a context merger function
|
|
490
|
+
*/
|
|
491
|
+
declare function isContextMergerFunction(value: unknown): value is ContextMergerFunction;
|
|
492
|
+
/**
|
|
493
|
+
* Type guard to check if value is ListenerOptions
|
|
494
|
+
*/
|
|
495
|
+
declare function isListenerOptions(value: unknown): value is ListenerOptions;
|
|
496
|
+
/**
|
|
497
|
+
* Type guard to check if value is IKernelEvent
|
|
498
|
+
*/
|
|
499
|
+
declare function isKernelEvent<T = any>(value: unknown): value is IKernelEvent<T>;
|
|
500
|
+
/**
|
|
501
|
+
* Extract event names from an EventMap
|
|
502
|
+
*/
|
|
503
|
+
type EventNames<E extends EventMap> = keyof E;
|
|
504
|
+
/**
|
|
505
|
+
* Extract event data type for a specific event
|
|
506
|
+
*/
|
|
507
|
+
type EventDataType<E extends EventMap, K extends keyof E> = E[K];
|
|
508
|
+
/**
|
|
509
|
+
* Unbind function returned by on() and once()
|
|
510
|
+
*/
|
|
511
|
+
type UnbindFunction = () => void;
|
|
512
|
+
/**
|
|
513
|
+
* Error thrown when circular dependencies are detected
|
|
514
|
+
*/
|
|
515
|
+
declare class CircularDependencyError extends Error {
|
|
516
|
+
constructor(cycle: string[]);
|
|
517
|
+
}
|
|
518
|
+
/**
|
|
519
|
+
* Error thrown when a listener dependency is missing
|
|
520
|
+
*/
|
|
521
|
+
declare class MissingDependencyError extends Error {
|
|
522
|
+
constructor(listenerId: string, missingDep: string);
|
|
523
|
+
}
|
|
524
|
+
/**
|
|
525
|
+
* Error thrown when max listeners exceeded
|
|
526
|
+
*/
|
|
527
|
+
declare class MaxListenersExceededError extends Error {
|
|
528
|
+
constructor(event: string, max: number);
|
|
529
|
+
}
|
|
530
|
+
|
|
531
|
+
/**
|
|
532
|
+
* Composition class - Merges multiple kernels into a unified interface
|
|
533
|
+
*
|
|
534
|
+
* Subscribes to events from multiple kernels, buffers them, and emits
|
|
535
|
+
* composite events when all source events have fired. Contexts are merged
|
|
536
|
+
* using a configurable ContextMerger strategy.
|
|
537
|
+
*/
|
|
538
|
+
|
|
539
|
+
/**
|
|
540
|
+
* Buffered event entry for a source kernel
|
|
541
|
+
*/
|
|
542
|
+
interface BufferedEvent {
|
|
543
|
+
name: string;
|
|
544
|
+
data: any;
|
|
545
|
+
context: Record<string, any>;
|
|
546
|
+
timestamp: number;
|
|
547
|
+
}
|
|
548
|
+
/**
|
|
549
|
+
* Composition class that merges events from multiple kernels
|
|
550
|
+
*
|
|
551
|
+
* Example:
|
|
552
|
+
* ```ts
|
|
553
|
+
* const userKernel = createKernel();
|
|
554
|
+
* const profileKernel = createKernel();
|
|
555
|
+
*
|
|
556
|
+
* const composition = new Composition([
|
|
557
|
+
* [userKernel, 'user:loaded'],
|
|
558
|
+
* [profileKernel, 'profile:loaded'],
|
|
559
|
+
* ], {
|
|
560
|
+
* merger: createNamespacedMerger(),
|
|
561
|
+
* bufferLimit: 100,
|
|
562
|
+
* });
|
|
563
|
+
*
|
|
564
|
+
* composition.onComposed((event) => {
|
|
565
|
+
* // event.data.merged contains merged contexts from all sources
|
|
566
|
+
* });
|
|
567
|
+
* ```
|
|
568
|
+
*/
|
|
569
|
+
declare class Composition<Events extends EventMap = EventMap> {
|
|
570
|
+
private kernel;
|
|
571
|
+
private subscriptions;
|
|
572
|
+
private buffers;
|
|
573
|
+
private merger;
|
|
574
|
+
private bufferLimit;
|
|
575
|
+
private reset;
|
|
576
|
+
private eventTTL;
|
|
577
|
+
private eventTTLs;
|
|
578
|
+
private sourceEvents;
|
|
579
|
+
private firedSinceLastComposite;
|
|
580
|
+
private lastConflicts;
|
|
581
|
+
private expirationTimers;
|
|
582
|
+
/**
|
|
583
|
+
* Create a new Composition
|
|
584
|
+
*
|
|
585
|
+
* @param kernels - Array of [kernel, eventName] tuples to subscribe to
|
|
586
|
+
* @param options - Composition options
|
|
587
|
+
*/
|
|
588
|
+
constructor(kernels: Array<[Kernel, EventName$1]>, options?: CompositionOptions$1);
|
|
589
|
+
/**
|
|
590
|
+
* Subscribe to events from a source kernel
|
|
591
|
+
*/
|
|
592
|
+
private subscribeToKernel;
|
|
593
|
+
/**
|
|
594
|
+
* Get the effective TTL for a specific event
|
|
595
|
+
* Priority: per-event TTL > global TTL > 0 (permanent)
|
|
596
|
+
*/
|
|
597
|
+
private getEffectiveTTL;
|
|
598
|
+
/**
|
|
599
|
+
* Handle an event from a source kernel
|
|
600
|
+
*/
|
|
601
|
+
private handleSourceEvent;
|
|
602
|
+
/**
|
|
603
|
+
* Expire an event from the buffer based on timestamp
|
|
604
|
+
*/
|
|
605
|
+
private expireEvent;
|
|
606
|
+
/**
|
|
607
|
+
* Check if all source events have fired and emit composite event
|
|
608
|
+
* @returns true if composite was emitted, false otherwise
|
|
609
|
+
*/
|
|
610
|
+
private checkAndEmitComposite;
|
|
611
|
+
/**
|
|
612
|
+
* Register a listener for when all source events have fired
|
|
613
|
+
* This is the primary way to react to composition completion
|
|
614
|
+
*
|
|
615
|
+
* @param listener - Function called with merged context when composition completes
|
|
616
|
+
* @param options - Listener options (priority, id, etc.)
|
|
617
|
+
* @returns Unbind function to remove the listener
|
|
618
|
+
*/
|
|
619
|
+
onComposed(listener: ListenerFunction<Events[keyof Events]>, options?: ListenerOptions): () => void;
|
|
620
|
+
/**
|
|
621
|
+
* Remove a listener for composed events
|
|
622
|
+
*/
|
|
623
|
+
offComposed(listener?: Function): void;
|
|
624
|
+
/**
|
|
625
|
+
* Get number of composed event listeners
|
|
626
|
+
*/
|
|
627
|
+
composedListenerCount(): number;
|
|
628
|
+
/**
|
|
629
|
+
* Register a listener for events on internal kernel
|
|
630
|
+
* Note: Use onComposed() to listen for composition completion
|
|
631
|
+
*/
|
|
632
|
+
on<K extends keyof Events>(eventName: K, listener: ListenerFunction<Events[K]>, options?: ListenerOptions): () => void;
|
|
633
|
+
/**
|
|
634
|
+
* Remove a listener
|
|
635
|
+
* Delegates to internal kernel
|
|
636
|
+
*/
|
|
637
|
+
off(eventName: string, listener?: Function): void;
|
|
638
|
+
/**
|
|
639
|
+
* Emit an event through the composition
|
|
640
|
+
* Note: Reserved internal events (prefixed with __qk:) cannot be emitted
|
|
641
|
+
*/
|
|
642
|
+
emit<K extends keyof Events>(eventName: K, data?: Events[K]): Promise<void>;
|
|
643
|
+
/**
|
|
644
|
+
* Get merged context from latest buffered events
|
|
645
|
+
* Does not emit - just returns the merged context
|
|
646
|
+
*/
|
|
647
|
+
getContext(): Record<string, any> | null;
|
|
648
|
+
/**
|
|
649
|
+
* Get number of listeners for an event
|
|
650
|
+
*/
|
|
651
|
+
listenerCount(eventName?: keyof Events): number;
|
|
652
|
+
/**
|
|
653
|
+
* Get all event names with registered listeners
|
|
654
|
+
*/
|
|
655
|
+
eventNames(): (keyof Events)[];
|
|
656
|
+
/**
|
|
657
|
+
* Remove all listeners
|
|
658
|
+
*/
|
|
659
|
+
offAll(eventName?: keyof Events): void;
|
|
660
|
+
/**
|
|
661
|
+
* Enable/disable debug mode
|
|
662
|
+
*/
|
|
663
|
+
debug(enabled: boolean): void;
|
|
664
|
+
/**
|
|
665
|
+
* Get buffer for a specific source event (for debugging)
|
|
666
|
+
*/
|
|
667
|
+
getBuffer(eventName: EventName$1): ReadonlyArray<BufferedEvent> | undefined;
|
|
668
|
+
/**
|
|
669
|
+
* Clear all buffers
|
|
670
|
+
*/
|
|
671
|
+
clearBuffers(): void;
|
|
672
|
+
/**
|
|
673
|
+
* Get conflicts detected during the last merge operation
|
|
674
|
+
*
|
|
675
|
+
* Returns an array of ConflictInfo objects describing which source events
|
|
676
|
+
* provided conflicting values for the same context keys.
|
|
677
|
+
*
|
|
678
|
+
* @returns Array of conflicts from the last merge, or empty array if no conflicts
|
|
679
|
+
*/
|
|
680
|
+
getConflicts(): ReadonlyArray<ConflictInfo>;
|
|
681
|
+
/**
|
|
682
|
+
* Cleanup all subscriptions and listeners
|
|
683
|
+
*/
|
|
684
|
+
dispose(): void;
|
|
685
|
+
/**
|
|
686
|
+
* Get the configured global event TTL in milliseconds
|
|
687
|
+
* @returns The TTL value, or 0 if no TTL is configured
|
|
688
|
+
*/
|
|
689
|
+
getEventTTL(): number;
|
|
690
|
+
/**
|
|
691
|
+
* Set the global event TTL in milliseconds
|
|
692
|
+
* @param ttl - TTL in milliseconds (0 = permanent)
|
|
693
|
+
*/
|
|
694
|
+
setEventTTL(ttl: number): void;
|
|
695
|
+
/**
|
|
696
|
+
* Get per-event TTL configuration
|
|
697
|
+
* @returns The eventTTLs configuration object
|
|
698
|
+
*/
|
|
699
|
+
getEventTTLs(): Readonly<Record<EventName$1, number | 'permanent' | 'instant'>>;
|
|
700
|
+
/**
|
|
701
|
+
* Set TTL for a specific event
|
|
702
|
+
* @param eventName - The event name to configure
|
|
703
|
+
* @param ttl - TTL value: number (ms), 'permanent', or 'instant'
|
|
704
|
+
*/
|
|
705
|
+
setEventTTLFor(eventName: EventName$1, ttl: number | 'permanent' | 'instant'): void;
|
|
706
|
+
/**
|
|
707
|
+
* Remove per-event TTL configuration (falls back to global TTL)
|
|
708
|
+
* @param eventName - The event name to reset
|
|
709
|
+
*/
|
|
710
|
+
clearEventTTLFor(eventName: EventName$1): void;
|
|
711
|
+
}
|
|
712
|
+
/**
|
|
713
|
+
* Factory function to create a Composition instance
|
|
714
|
+
*/
|
|
715
|
+
declare const createComposition: <Events extends EventMap = EventMap>(kernels: Array<[Kernel, EventName$1]>, options?: CompositionOptions$1) => Composition<Events>;
|
|
716
|
+
|
|
717
|
+
/**
|
|
718
|
+
* QuarKernel Core Implementation
|
|
719
|
+
*
|
|
720
|
+
* A TypeScript event kernel with:
|
|
721
|
+
* - Priority-based listener ordering
|
|
722
|
+
* - Shared context between listeners
|
|
723
|
+
* - Async-first with Promise-based API
|
|
724
|
+
* - Arrow functions only (no `this` binding)
|
|
725
|
+
*/
|
|
726
|
+
|
|
727
|
+
/**
|
|
728
|
+
* Error collected during event execution
|
|
729
|
+
*/
|
|
730
|
+
interface ExecutionError {
|
|
731
|
+
listenerId: string;
|
|
732
|
+
error: Error;
|
|
733
|
+
timestamp: number;
|
|
734
|
+
eventName: string;
|
|
735
|
+
}
|
|
736
|
+
/**
|
|
737
|
+
* Core Kernel class
|
|
738
|
+
* Implements basic on(), off(), emit() with Map-based storage
|
|
739
|
+
*/
|
|
740
|
+
declare class Kernel<Events extends EventMap = EventMap> implements ListenerContextKernel {
|
|
741
|
+
private listeners;
|
|
742
|
+
private options;
|
|
743
|
+
private listenerIdCounter;
|
|
744
|
+
private executionErrors;
|
|
745
|
+
constructor(options?: KernelOptions);
|
|
746
|
+
/**
|
|
747
|
+
* Register an event listener
|
|
748
|
+
* Returns an unbind function for cleanup
|
|
749
|
+
*/
|
|
750
|
+
on<K extends keyof Events>(eventName: K, listener: ListenerFunction<Events[K]>, options?: ListenerOptions): () => void;
|
|
751
|
+
/**
|
|
752
|
+
* Remove an event listener
|
|
753
|
+
* If no listener provided, removes all listeners for the event
|
|
754
|
+
*/
|
|
755
|
+
off(eventName: string, listener?: Function): void;
|
|
756
|
+
/**
|
|
757
|
+
* Emit an event
|
|
758
|
+
* Executes all registered listeners in parallel (by default)
|
|
759
|
+
* Returns a Promise that resolves when all listeners complete
|
|
760
|
+
* Throws AggregateError if any listeners failed
|
|
761
|
+
*/
|
|
762
|
+
emit<K extends keyof Events>(eventName: K, data?: Events[K]): Promise<void>;
|
|
763
|
+
/**
|
|
764
|
+
* Emit an event with serial execution
|
|
765
|
+
* Executes listeners sequentially (one after another) instead of in parallel
|
|
766
|
+
* Respects the same dependency and priority ordering as emit()
|
|
767
|
+
* Stops on first error if errorBoundary is false, otherwise continues and collects errors
|
|
768
|
+
*/
|
|
769
|
+
emitSerial<K extends keyof Events>(eventName: K, data?: Events[K]): Promise<void>;
|
|
770
|
+
/**
|
|
771
|
+
* Sort listeners by dependencies and priority
|
|
772
|
+
* Uses topological sort for dependency resolution
|
|
773
|
+
*/
|
|
774
|
+
private sortListenersByDependencies;
|
|
775
|
+
/**
|
|
776
|
+
* Execute a single listener with error handling
|
|
777
|
+
*/
|
|
778
|
+
private executeListener;
|
|
779
|
+
/**
|
|
780
|
+
* Remove listeners marked with once: true or whose predicate returns true after execution
|
|
781
|
+
*
|
|
782
|
+
* This method is called AFTER all listeners have executed for an event.
|
|
783
|
+
* The predicate functions receive the event object with the final state after all listeners ran.
|
|
784
|
+
*
|
|
785
|
+
* Behavior:
|
|
786
|
+
* - If once: true, the listener is always removed after execution
|
|
787
|
+
* - If once is a predicate function, it's evaluated with the post-execution event state
|
|
788
|
+
* - Predicates can examine event.context to make decisions based on listener modifications
|
|
789
|
+
* - Listeners are removed even if they threw errors (when errorBoundary: true)
|
|
790
|
+
*
|
|
791
|
+
* @param eventName - The event name being processed
|
|
792
|
+
* @param entries - Listeners that executed (or were scheduled to execute)
|
|
793
|
+
* @param event - The event object with final state after all listeners executed
|
|
794
|
+
*/
|
|
795
|
+
private removeOnceListeners;
|
|
796
|
+
/**
|
|
797
|
+
* Get number of listeners for an event
|
|
798
|
+
*/
|
|
799
|
+
listenerCount(eventName?: keyof Events): number;
|
|
800
|
+
/**
|
|
801
|
+
* Get all event names with registered listeners
|
|
802
|
+
*/
|
|
803
|
+
eventNames(): (keyof Events)[];
|
|
804
|
+
/**
|
|
805
|
+
* Remove all listeners for all events (or specific event)
|
|
806
|
+
*/
|
|
807
|
+
offAll(eventName?: keyof Events): void;
|
|
808
|
+
/**
|
|
809
|
+
* Enable/disable debug mode
|
|
810
|
+
* In T115, this is a placeholder - full debug implementation in T129
|
|
811
|
+
*/
|
|
812
|
+
debug(enabled: boolean): void;
|
|
813
|
+
/**
|
|
814
|
+
* Get collected execution errors from the last emit
|
|
815
|
+
* Useful for error aggregation and reporting
|
|
816
|
+
*/
|
|
817
|
+
getExecutionErrors(): ReadonlyArray<ExecutionError>;
|
|
818
|
+
/**
|
|
819
|
+
* Clear collected execution errors
|
|
820
|
+
*/
|
|
821
|
+
clearExecutionErrors(): void;
|
|
822
|
+
/**
|
|
823
|
+
* Create a composition from multiple kernels
|
|
824
|
+
*
|
|
825
|
+
* @param kernels - Rest parameters of [kernel, eventName] tuples
|
|
826
|
+
* @param options - Optional composition options (if last argument is not a tuple)
|
|
827
|
+
* @returns Composition instance that merges events from all kernels
|
|
828
|
+
*
|
|
829
|
+
* @example
|
|
830
|
+
* ```ts
|
|
831
|
+
* const userKernel = createKernel();
|
|
832
|
+
* const profileKernel = createKernel();
|
|
833
|
+
*
|
|
834
|
+
* const composition = Kernel.compose(
|
|
835
|
+
* [userKernel, 'user:loaded'],
|
|
836
|
+
* [profileKernel, 'profile:loaded'],
|
|
837
|
+
* { merger: createNamespacedMerger() }
|
|
838
|
+
* );
|
|
839
|
+
*
|
|
840
|
+
* composition.onComposed((event) => {
|
|
841
|
+
* console.log('All sources ready:', event.data.merged);
|
|
842
|
+
* });
|
|
843
|
+
* ```
|
|
844
|
+
*/
|
|
845
|
+
static compose<Events extends EventMap = EventMap>(...args: (readonly [Kernel, EventName$1] | CompositionOptions$1)[]): Composition<Events>;
|
|
846
|
+
}
|
|
847
|
+
/**
|
|
848
|
+
* Factory function to create a Kernel instance
|
|
849
|
+
*/
|
|
850
|
+
declare const createKernel: <Events extends EventMap = EventMap>(options?: KernelOptions) => Kernel<Events>;
|
|
851
|
+
|
|
852
|
+
/**
|
|
853
|
+
* FSM Machine Implementation
|
|
854
|
+
*
|
|
855
|
+
* Flexible state machine layer built on quarkernel events.
|
|
856
|
+
* Uses prefixed events for loose coupling and multi-machine orchestration.
|
|
857
|
+
*/
|
|
858
|
+
|
|
859
|
+
/**
|
|
860
|
+
* Create a state machine on a kernel
|
|
861
|
+
*
|
|
862
|
+
* @param kernel - The quarkernel instance to use
|
|
863
|
+
* @param config - Machine configuration
|
|
864
|
+
* @returns Machine instance
|
|
865
|
+
*
|
|
866
|
+
* @example
|
|
867
|
+
* ```ts
|
|
868
|
+
* const kernel = new Kernel();
|
|
869
|
+
*
|
|
870
|
+
* const order = useMachine(kernel, {
|
|
871
|
+
* prefix: 'order',
|
|
872
|
+
* initial: 'draft',
|
|
873
|
+
* states: {
|
|
874
|
+
* draft: { on: { SUBMIT: 'pending' } },
|
|
875
|
+
* pending: { on: { APPROVE: 'confirmed', REJECT: 'draft' } },
|
|
876
|
+
* confirmed: { on: { SHIP: 'shipped' } },
|
|
877
|
+
* shipped: {}
|
|
878
|
+
* }
|
|
879
|
+
* });
|
|
880
|
+
*
|
|
881
|
+
* // Listen to state changes
|
|
882
|
+
* kernel.on('order:enter:confirmed', (e) => {
|
|
883
|
+
* console.log('Order confirmed!');
|
|
884
|
+
* });
|
|
885
|
+
*
|
|
886
|
+
* await order.send('SUBMIT');
|
|
887
|
+
* await order.send('APPROVE');
|
|
888
|
+
* ```
|
|
889
|
+
*/
|
|
890
|
+
declare function useMachine<TContext = Record<string, any>>(kernel: Kernel, config: MachineConfig<TContext>): Machine<TContext>;
|
|
891
|
+
/**
|
|
892
|
+
* Type helper for defining typed machine configs
|
|
893
|
+
*/
|
|
894
|
+
declare function defineMachine<TContext = Record<string, any>>(config: Omit<MachineConfig<TContext>, 'prefix'>): Omit<MachineConfig<TContext>, 'prefix'>;
|
|
895
|
+
|
|
896
|
+
export { isListenerOptions as A, isKernelEvent as B, type ContextMerger$1 as C, CircularDependencyError as D, type EventName$1 as E, MaxListenersExceededError as F, useMachine as G, defineMachine as H, type IKernelEvent as I, KernelEvent as K, ListenerContext as L, MissingDependencyError as M, type PredicateFunction as P, type UnbindFunction as U, Kernel as a, Composition as b, createKernel as c, createComposition as d, type ConflictInfo as e, type CompositionOptions$1 as f, type EventName as g, type EventData as h, type EventMap as i, type IKernel as j, type IListenerContext as k, type ListenerFunction as l, type ListenerOptions as m, type ListenerEntry as n, type KernelOptions as o, type EventStack as p, type CompositionFactory as q, type IComposition as r, type ContextMergerFunction as s, type EventNames as t, type EventDataType as u, isEventName as v, isListenerFunction as w, isPredicateFunction as x, isContextMerger as y, isContextMergerFunction as z };
|