From 04ce10fec39c085f36ae11e52635f3b9a7922cea Mon Sep 17 00:00:00 2001 From: Chakib Benziane Date: Fri, 7 Dec 2018 16:50:29 +0100 Subject: [PATCH] manager --- manager.go | 109 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 109 insertions(+) create mode 100644 manager.go diff --git a/manager.go b/manager.go new file mode 100644 index 0000000..bd3e7a3 --- /dev/null +++ b/manager.go @@ -0,0 +1,109 @@ +package gum + +import ( + "log" + "os" + "os/signal" + "reflect" + "strings" +) + +type WorkUnit interface { + Spawn(UnitManager) + Shutdown() +} + +type UnitManager interface { + ShouldStop() <-chan bool + Done() +} + +type WorkUnitManager struct { + stop chan bool + workerQuit chan bool + unit WorkUnit +} + +func (w *WorkUnitManager) ShouldStop() <-chan bool { + return w.stop +} + +func (w *WorkUnitManager) Done() { + w.workerQuit <- true +} + +type Manager struct { + signal chan os.Signal + + workers map[string]*WorkUnitManager + + quit chan bool +} + +func (m *Manager) Start() { + log.Println("Starting manager ...") + + for unitName, w := range m.workers { + log.Printf("Starting <%s>\n", unitName) + go w.unit.Spawn(w) + } + + for { + select { + case sig := <-m.signal: + if sig != os.Interrupt { + break + } + + log.Println("shutting event received ... ") + + // send shutdown event to all worker units + for name, w := range m.workers { + log.Printf("shuting down <%s>\n", name) + w.stop <- true + } + + // Wait for all units to quit + for name, w := range m.workers { + <-w.workerQuit + log.Printf("<%s> down", name) + } + + // All workers have shutdown + log.Println("All workers have shutdown, shutting down manager ...") + + DB.Handle.Close() + m.quit <- true + + } + } +} + +func (m *Manager) SubscribeTo(sig os.Signal) { + signal.Notify(m.signal, sig) +} + +func (m *Manager) AddUnit(unit WorkUnit) { + + workUnitManager := &WorkUnitManager{ + workerQuit: make(chan bool, 1), + stop: make(chan bool, 1), + unit: unit, + } + + unitType := reflect.TypeOf(unit) + unitName := strings.Split(unitType.String(), ".")[1] + + log.Println("Adding unit ", unitName) + + m.workers[unitName] = workUnitManager + log.Println(m.workers) +} + +func NewManager() *Manager { + return &Manager{ + signal: make(chan os.Signal, 1), + quit: make(chan bool), + workers: make(map[string]*WorkUnitManager), + } +}