github.com/haraldrudell/parl@v0.4.176/counter/runner.go (about) 1 /* 2 © 2022–present Harald Rudell <harald.rudell@gmail.com> (https://haraldrudell.github.io/haraldrudell/) 3 ISC License 4 */ 5 6 package counter 7 8 import ( 9 "sync" 10 "time" 11 ) 12 13 // runner is a container executing rate-counters for a particular interval 14 type runner struct { 15 lock sync.RWMutex 16 tasks []RateRunnerTask // behind lock 17 } 18 19 // runner returns a container for rate-counters of a particular interval 20 func NewRunner() (run *runner) { 21 return &runner{} 22 } 23 24 // Add adds an additional rate-counter to this container 25 func (r *runner) Add(task RateRunnerTask) { 26 r.lock.Lock() 27 defer r.lock.Unlock() 28 29 r.tasks = append(r.tasks, task) 30 } 31 32 // Do is invoked by a timer with an intended at time 33 func (r *runner) Do(at time.Time) { 34 at = time.Now() // obtain accurate time-stamp 35 for i := 0; ; i++ { 36 task := r.task(i) 37 if task == nil { 38 return 39 } 40 task.Do(at) 41 } 42 } 43 44 // task returns task n 0…, nil if no such task exists 45 func (r *runner) task(i int) (task RateRunnerTask) { 46 r.lock.RLock() 47 defer r.lock.RUnlock() 48 49 if i < 0 || i >= len(r.tasks) { 50 return 51 } 52 task = r.tasks[i] 53 return 54 }