reworked thread to use queue instead of single action

graph-rework-2
noah metz 2023-07-24 17:49:26 -06:00
parent 2e77b811d5
commit 3fa550ab29
1 changed files with 30 additions and 17 deletions

@ -160,8 +160,8 @@ func NewChildInfo(child ThreadNode, infos map[InfoType]interface{}) ChildInfo {
}
type QueuedAction struct {
Timeout time.Time
Action string
Timeout time.Time `json:"time"`
Action string `json:"action"`
}
type ThreadNode interface {
@ -185,9 +185,13 @@ type Thread struct {
Parent ThreadNode
Children map[NodeID]ChildInfo
InfoTypes []InfoType
TimeoutAction string
Timeout time.Time
ActionQueue []QueuedAction
NextAction *QueuedAction
}
func (thread *Thread) QueueAction(end time.Time, action string) {
thread.ActionQueue = append(thread.ActionQueue, QueuedAction{end, action})
thread.NextAction, thread.TimeoutChan = thread.SoonestAction()
}
func (thread *Thread) ThreadHandle() *Thread {
@ -216,8 +220,7 @@ func (thread *Thread) ChildList() []ThreadNode {
type ThreadJSON struct {
Parent string `json:"parent"`
Children map[string]map[string]interface{} `json:"children"`
Timeout time.Time `json:"timeout"`
TimeoutAction string `json:"timeout_action"`
ActionQueue []QueuedAction `json:"action_queue"`
StateName string `json:"state_name"`
LockableJSON
}
@ -242,8 +245,7 @@ func NewThreadJSON(thread *Thread) ThreadJSON {
return ThreadJSON{
Parent: parent_id,
Children: children,
Timeout: thread.Timeout,
TimeoutAction: thread.TimeoutAction,
ActionQueue: thread.ActionQueue,
StateName: thread.StateName,
LockableJSON: lockable_json,
}
@ -267,11 +269,24 @@ func LoadThread(ctx *Context, id NodeID, data []byte, nodes NodeMap) (Node, erro
return &thread, nil
}
func RestoreThread(ctx *Context, thread *Thread, j ThreadJSON, nodes NodeMap) error {
if j.TimeoutAction != "" {
thread.Timeout = j.Timeout
thread.TimeoutAction = j.TimeoutAction
func (thread *Thread) SoonestAction() (*QueuedAction, <-chan time.Time) {
var soonest_action *QueuedAction
var soonest_time time.Time
for _, action := range(thread.ActionQueue) {
if action.Timeout.Compare(soonest_time) == -1 {
soonest_action = &action
}
}
if soonest_action != nil {
return soonest_action, time.After(time.Until(soonest_action.Timeout))
} else {
return nil, nil
}
}
func RestoreThread(ctx *Context, thread *Thread, j ThreadJSON, nodes NodeMap) error {
thread.ActionQueue = j.ActionQueue
thread.NextAction, thread.TimeoutChan = thread.SoonestAction()
if j.Parent != "" {
parent_id, err := ParseID(j.Parent)
@ -574,7 +589,7 @@ func ThreadStart(ctx * Context, node ThreadNode) (string, error) {
func ThreadWait(ctx * Context, node ThreadNode) (string, error) {
thread := node.ThreadHandle()
ctx.Log.Logf("thread", "THREAD_WAIT: %s TIMEOUT: %+v", thread.ID(), thread.Timeout)
ctx.Log.Logf("thread", "THREAD_WAIT: %s", thread.ID())
for {
select {
case signal := <- thread.Chan:
@ -590,10 +605,8 @@ func ThreadWait(ctx * Context, node ThreadNode) (string, error) {
timeout_action := ""
context := NewWriteContext(ctx)
err := UpdateStates(context, thread, NewLockMap(NewLockInfo(thread, []string{"timeout"})), func(context *StateContext) error {
timeout_action = thread.TimeoutAction
thread.TimeoutChan = nil
thread.TimeoutAction = ""
thread.Timeout = time.Time{}
timeout_action = thread.NextAction.Action
thread.NextAction, thread.TimeoutChan = thread.SoonestAction()
return nil
})
if err != nil {