@ -37,6 +37,7 @@ type (
confirmChan chan lang . PlaceholderType
confirmChan chan lang . PlaceholderType
guarded bool
guarded bool
newTicker func ( duration time . Duration ) timex . Ticker
newTicker func ( duration time . Duration ) timex . Ticker
currTask int
lock sync . Mutex
lock sync . Mutex
}
}
)
)
@ -103,7 +104,9 @@ func (pe *PeriodicalExecutor) addAndCheck(task interface{}) (interface{}, bool)
} ( )
} ( )
if pe . container . AddTask ( task ) {
if pe . container . AddTask ( task ) {
return pe . container . RemoveAll ( ) , true
vals := pe . container . RemoveAll ( )
pe . currTask ++
return vals , true
}
}
return nil , false
return nil , false
@ -122,6 +125,9 @@ func (pe *PeriodicalExecutor) backgroundFlush() {
commanded = true
commanded = true
pe . enterExecution ( )
pe . enterExecution ( )
pe . confirmChan <- lang . Placeholder
pe . confirmChan <- lang . Placeholder
pe . lock . Lock ( )
pe . currTask --
pe . lock . Unlock ( )
pe . executeTasks ( vals )
pe . executeTasks ( vals )
last = timex . Now ( )
last = timex . Now ( )
case <- ticker . Chan ( ) :
case <- ticker . Chan ( ) :
@ -130,33 +136,25 @@ func (pe *PeriodicalExecutor) backgroundFlush() {
} else if pe . Flush ( ) {
} else if pe . Flush ( ) {
last = timex . Now ( )
last = timex . Now ( )
} else if timex . Since ( last ) > pe . interval * idleRound {
} else if timex . Since ( last ) > pe . interval * idleRound {
var exit bool = true
pe . lock . Lock ( )
pe . lock . Lock ( )
if pe . currTask > 0 {
exit = false
} else {
pe . guarded = false
pe . guarded = false
pe . lock . Unlock ( )
pe . cleanup ( )
return
}
}
}
} )
}
}
pe . lock . Unlock ( )
func ( pe * PeriodicalExecutor ) cleanup ( ) {
if exit {
// avoid deadlock in Add()
for {
select {
case vals := <- pe . commander :
pe . enterExecution ( )
pe . confirmChan <- lang . Placeholder
pe . executeTasks ( vals )
default :
// flush again to avoid missing tasks
// flush again to avoid missing tasks
pe . Flush ( )
pe . Flush ( )
return
return
}
}
}
}
}
}
}
} )
}
func ( pe * PeriodicalExecutor ) doneExecution ( ) {
func ( pe * PeriodicalExecutor ) doneExecution ( ) {
pe . waitGroup . Done ( )
pe . waitGroup . Done ( )