@@ -70,15 +70,21 @@ func WithAsync() FSMOption {
70
70
}
71
71
}
72
72
73
+ func WithInSeq () FSMOption {
74
+ return func (fsm * FSM ) {
75
+ fsm .inseq = true
76
+ }
77
+ }
78
+
73
79
type FSM struct {
74
80
state string
75
81
states map [string ]* State
76
82
events map [string ]* list.List
77
83
78
- async bool
79
- mutex sync.RWMutex
80
- pq * prioqueue.PrioQueue
81
- cancel context.CancelFunc
84
+ async , inseq bool
85
+ mutex sync.RWMutex
86
+ pq * prioqueue.PrioQueue
87
+ cancel context.CancelFunc
82
88
}
83
89
84
90
func NewFSM (opts ... FSMOption ) * FSM {
@@ -182,6 +188,49 @@ func (fsm *FSM) emitOne() {
182
188
}
183
189
}
184
190
191
+ func (fsm * FSM ) emitOneInSeq () {
192
+ fsm .mutex .Lock ()
193
+ defer fsm .mutex .Unlock ()
194
+
195
+ data := fsm .pq .PopSync ()
196
+ if data == nil {
197
+ return
198
+ }
199
+ switch ec := data .(type ) {
200
+ case * eventchan :
201
+ et := (* Event )(nil )
202
+ etList , ok := fsm .events [ec .event ]
203
+ if ! ok {
204
+ ec .ch <- ErrEventNotExist
205
+ close (ec .ch )
206
+ return
207
+ }
208
+ for elem := etList .Front (); elem != nil ; elem = elem .Next () {
209
+ tmp := elem .Value .(* Event )
210
+ if tmp .From .State == fsm .state {
211
+ et = tmp
212
+ }
213
+ }
214
+ if et == nil {
215
+ ec .ch <- ErrIllegalStateForEvent
216
+ close (ec .ch )
217
+ return
218
+ }
219
+ fsm .state = et .To .State
220
+ for _ , left := range et .From .lefts {
221
+ left (et .From )
222
+ }
223
+ for _ , handler := range et .handlers {
224
+ handler (et )
225
+ }
226
+ for _ , enter := range et .To .enters {
227
+ enter (et .To )
228
+ }
229
+ ec .ch <- nil
230
+ close (ec .ch )
231
+ }
232
+ }
233
+
185
234
func (fsm * FSM ) SetState (state string ) bool {
186
235
fsm .mutex .Lock ()
187
236
defer fsm .mutex .Unlock ()
@@ -411,7 +460,11 @@ func (fsm *FSM) EmitEvent(event string) error {
411
460
return err
412
461
}
413
462
if ! fsm .async {
414
- fsm .emitOne ()
463
+ if fsm .inseq {
464
+ fsm .emitOneInSeq ()
465
+ } else {
466
+ fsm .emitOne ()
467
+ }
415
468
}
416
469
err = <- ch
417
470
return err
@@ -438,7 +491,11 @@ func (fsm *FSM) EmitEventAsync(event string) <-chan error {
438
491
return ch
439
492
}
440
493
if ! fsm .async {
441
- fsm .emitOne ()
494
+ if fsm .inseq {
495
+ fsm .emitOneInSeq ()
496
+ } else {
497
+ fsm .emitOne ()
498
+ }
442
499
}
443
500
return ch
444
501
}
@@ -462,7 +519,11 @@ func (fsm *FSM) EmitPrioEvent(prio int, event string) error {
462
519
return err
463
520
}
464
521
if ! fsm .async {
465
- fsm .emitOne ()
522
+ if fsm .inseq {
523
+ fsm .emitOneInSeq ()
524
+ } else {
525
+ fsm .emitOne ()
526
+ }
466
527
}
467
528
err = <- ch
468
529
return err
@@ -489,7 +550,11 @@ func (fsm *FSM) EmitPrioEventAsync(prio int, event string) <-chan error {
489
550
return ch
490
551
}
491
552
if ! fsm .async {
492
- fsm .emitOne ()
553
+ if fsm .inseq {
554
+ fsm .emitOneInSeq ()
555
+ } else {
556
+ fsm .emitOne ()
557
+ }
493
558
}
494
559
return ch
495
560
}
0 commit comments