@@ -54,7 +54,13 @@ export interface Send<Method extends string | symbol, Arguments extends any[]> {
54
54
args : Arguments ;
55
55
}
56
56
57
- export type Yielded = On | Always | Cond | EntryAction | ExitAction | ListenTo | Call < any > ;
57
+ export interface Accumulate {
58
+ type : "accumulate" ;
59
+ eventName : string | symbol ;
60
+ resultKey : symbol ;
61
+ }
62
+
63
+ export type Yielded = On | Always | Cond | EntryAction | ExitAction | ListenTo | Accumulate | Call < any > ;
58
64
59
65
export function on < Event extends string | symbol > ( event : Event , target : Target ) : On {
60
66
return { type : "on" , on : event , target } ;
@@ -99,10 +105,15 @@ export function compound(...targets: Array<StateDefinition>): Compound {
99
105
return { type : "compound" , targets } ;
100
106
}
101
107
108
+ export function accumulate ( eventName : string | symbol , resultKey : symbol ) : Accumulate {
109
+ return { type : "accumulate" , eventName, resultKey } ;
110
+ }
111
+
102
112
export interface MachineInstance extends Iterator < null | string | Record < string , string > , void , string | symbol > {
103
113
changeCount : number ;
104
114
current : null | string | Record < string , string > ;
105
115
results : null | Promise < unknown > ;
116
+ accumulations : Map < symbol | string , Array < symbol | string | Event > > ;
106
117
done : boolean ;
107
118
next ( arg : string | symbol ) : IteratorResult < null | string | Record < string , string > > &
108
119
PromiseLike < any > & {
@@ -120,6 +131,7 @@ class Handlers {
120
131
private actionResults = new Map < string | symbol , unknown > ( ) ;
121
132
private promise : null | Promise < Array < unknown > > = null ;
122
133
public readonly eventsToListenTo = new Array < [ string , EventTarget ] > ( ) ;
134
+ public readonly eventsToAccumulate = new Array < [ string | symbol , symbol ] > ( ) ;
123
135
124
136
* actions ( ) : Generator < EntryAction , void , undefined > {
125
137
yield * this . entryActions ;
@@ -171,6 +183,8 @@ class Handlers {
171
183
this . alwaysArray . push ( value ) ;
172
184
} else if ( value . type === 'listenTo' ) {
173
185
this . eventsToListenTo . push ( [ value . eventName , value . sender ] ) ;
186
+ } else if ( value . type === 'accumulate' ) {
187
+ this . eventsToAccumulate . push ( [ value . eventName , value . resultKey ] ) ;
174
188
}
175
189
}
176
190
@@ -207,6 +221,7 @@ class InternalInstance {
207
221
private parent : null | InternalInstance
208
222
private globalHandlers = new Handlers ( )
209
223
private resolved = null as Promise < Record < string , any > > | null
224
+ private accumulations : Map < symbol | string , Array < symbol | string | Event > > = new Map ( ) ;
210
225
private eventAborter = new AbortController ( ) ;
211
226
child : null | InternalInstance = null
212
227
@@ -266,8 +281,19 @@ class InternalInstance {
266
281
// return build().then(pairs => Object.fromEntries(pairs as any));
267
282
}
268
283
284
+ * allAccumulations ( ) : Generator < [ symbol | string , Array < string | symbol | Event > ] > /*: Generator<{ key: symbol | string, events: Array<string | symbol | Event> }>*/ {
285
+ for ( const [ key , events ] of this . accumulations ) {
286
+ // yield { key, events };
287
+ yield [ key , events ] ;
288
+ }
289
+
290
+ if ( this . child !== null ) {
291
+ yield * this . child . allAccumulations ( ) ;
292
+ }
293
+ }
294
+
269
295
handleEvent ( event : Event ) {
270
- this . receive ( event . type ) ;
296
+ this . receive ( event ) ;
271
297
}
272
298
273
299
cleanup ( ) {
@@ -393,13 +419,23 @@ class InternalInstance {
393
419
return false ;
394
420
}
395
421
396
- receive ( event : string | symbol ) {
422
+ receive ( event : string | symbol | Event ) {
397
423
this . child ?. receive ( event ) ;
398
424
399
- const target = this . globalHandlers . targetForEvent ( event ) ;
425
+ const eventName = typeof event === 'string' || typeof event === 'symbol' ? event : event . type ;
426
+
427
+ const target = this . globalHandlers . targetForEvent ( eventName ) ;
400
428
if ( target !== undefined ) {
401
429
this . processTarget ( target ) ;
402
430
}
431
+
432
+ for ( const [ iteratedEventName , resultKey ] of this . globalHandlers . eventsToAccumulate ) {
433
+ if ( iteratedEventName === eventName ) {
434
+ const current = this . accumulations . get ( resultKey ) ?? [ ] ;
435
+ console . log ( "accumulating event" , eventName ) ;
436
+ this . accumulations . set ( resultKey , current . concat ( event ) ) ;
437
+ }
438
+ }
403
439
}
404
440
}
405
441
@@ -436,6 +472,9 @@ export function start(
436
472
get results ( ) {
437
473
return instance . results ;
438
474
} ,
475
+ get accumulations ( ) {
476
+ return new Map ( instance . allAccumulations ( ) ) ;
477
+ } ,
439
478
next ( event : string | symbol ) {
440
479
instance . receive ( event ) ;
441
480
const promise = instance . results ;
0 commit comments