task.go 798 B

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960
  1. package signal
  2. import (
  3. "sync"
  4. "time"
  5. )
  6. type PeriodicTask struct {
  7. Interval time.Duration
  8. Execute func() error
  9. access sync.Mutex
  10. timer *time.Timer
  11. closed bool
  12. }
  13. func (t *PeriodicTask) checkedExecute() error {
  14. t.access.Lock()
  15. defer t.access.Unlock()
  16. if t.closed {
  17. return nil
  18. }
  19. if err := t.Execute(); err != nil {
  20. return err
  21. }
  22. t.timer = time.AfterFunc(t.Interval, func() {
  23. t.checkedExecute()
  24. })
  25. return nil
  26. }
  27. func (t *PeriodicTask) Start() error {
  28. t.access.Lock()
  29. t.closed = false
  30. t.access.Unlock()
  31. if err := t.checkedExecute(); err != nil {
  32. t.closed = true
  33. return err
  34. }
  35. return nil
  36. }
  37. func (t *PeriodicTask) Close() error {
  38. t.access.Lock()
  39. defer t.access.Unlock()
  40. t.closed = true
  41. if t.timer != nil {
  42. t.timer.Stop()
  43. t.timer = nil
  44. }
  45. return nil
  46. }