package main import ( "log" "sync" "time" "srs.epita.fr/fic-server/settings" ) // distList maintain a nextSettingsFile list up-to-date. type distList struct { List []*settings.NextSettingsFile Lock sync.RWMutex Timer *time.Timer } // NewDistList creates a distList from the given src directory func NewDistList(src string) (*distList, error) { list, err := settings.ListNextSettingsFiles() if err != nil { return nil, err } return &distList{List: list, Timer: time.NewTimer(time.Minute)}, nil } func (l *distList) TimerNextEvent() *time.Timer { l.Lock.RLock() defer l.Lock.RUnlock() var min *time.Time for _, f := range l.List { if min == nil || f.Date.Before(*min) { min = &f.Date } } if min == nil { return nil } if min == nil { return nil } return time.NewTimer(time.Until(*min)) } func (l *distList) AddEvent(nsf *settings.NextSettingsFile) { l.Lock.Lock() istop := len(l.List) for i, n := range l.List { if n.Id == nsf.Id { return } else if n.Date.After(nsf.Date) { istop = i break } } l.List = append(l.List, nsf) copy(l.List[istop+1:], l.List[istop:]) l.List[istop] = nsf l.Lock.Unlock() if istop == 0 { l.ResetTimer() } } func (l *distList) DelEvent(id int64) { l.Lock.Lock() istop := len(l.List) for i, n := range l.List { if n.Id == id { istop = i break } } if istop == len(l.List)-1 { l.List = l.List[:istop] } else if istop != len(l.List) { l.List = append(l.List[:istop], l.List[istop+1:]...) } l.Lock.Unlock() if istop == 0 { l.ResetTimer() } } func (l *distList) ResetTimer() { l.Lock.RLock() defer l.Lock.RUnlock() if len(l.List) == 0 { l.Timer.Reset(time.Minute) } else { l.Timer.Reset(time.Until(l.List[0].Date)) } } func (l *distList) Pop() *settings.NextSettingsFile { l.Lock.Lock() defer l.Lock.Unlock() if len(l.List) == 0 { return nil } if time.Now().Before(l.List[0].Date) { return nil } ret := l.List[0] l.List = l.List[1:] return ret } func (l *distList) Print() { l.Lock.RLock() defer l.Lock.RUnlock() log.Println("Seeing distlist") for n, i := range l.List { log.Printf("#%d: %v", n, *i) } }