|
|
|
|
@ -1,8 +1,11 @@ |
|
|
|
|
package alerting |
|
|
|
|
|
|
|
|
|
import ( |
|
|
|
|
"math/rand" |
|
|
|
|
"strconv" |
|
|
|
|
"time" |
|
|
|
|
|
|
|
|
|
//"github.com/go-xorm/xorm"
|
|
|
|
|
"github.com/grafana/grafana/pkg/log" |
|
|
|
|
m "github.com/grafana/grafana/pkg/models" |
|
|
|
|
"github.com/grafana/grafana/pkg/setting" |
|
|
|
|
@ -23,19 +26,35 @@ func Init() { |
|
|
|
|
type Scheduler struct { |
|
|
|
|
jobs []*AlertJob |
|
|
|
|
runQueue chan *AlertJob |
|
|
|
|
|
|
|
|
|
serverId string |
|
|
|
|
serverPosition int |
|
|
|
|
clusterSize int |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func NewScheduler() *Scheduler { |
|
|
|
|
return &Scheduler{ |
|
|
|
|
jobs: make([]*AlertJob, 0), |
|
|
|
|
runQueue: make(chan *AlertJob, 1000), |
|
|
|
|
serverId: strconv.Itoa(rand.Intn(1000)), |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func (s *Scheduler) heartBeat() { |
|
|
|
|
//write heartBeat to db.
|
|
|
|
|
//get the modulus position of active servers
|
|
|
|
|
|
|
|
|
|
log.Info("Heartbeat: Sending heartbeat from " + s.serverId) |
|
|
|
|
s.clusterSize = 1 |
|
|
|
|
s.serverPosition = 1 |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func (s *Scheduler) Dispatch() { |
|
|
|
|
reschedule := time.NewTicker(time.Second * 10) |
|
|
|
|
secondTicker := time.NewTicker(time.Second) |
|
|
|
|
ticker := time.NewTicker(time.Second * 5) |
|
|
|
|
|
|
|
|
|
s.heartBeat() |
|
|
|
|
s.updateJobs() |
|
|
|
|
|
|
|
|
|
for { |
|
|
|
|
@ -44,41 +63,45 @@ func (s *Scheduler) Dispatch() { |
|
|
|
|
s.queueJobs() |
|
|
|
|
case <-reschedule.C: |
|
|
|
|
s.updateJobs() |
|
|
|
|
case <-ticker.C: |
|
|
|
|
s.heartBeat() |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func (s *Scheduler) getAlertRules() []m.AlertRule { |
|
|
|
|
return []m.AlertRule{ |
|
|
|
|
{Id: 1, Title: "alert rule 1", Interval: "10s", Frequency: 10}, |
|
|
|
|
{Id: 2, Title: "alert rule 2", Interval: "10s", Frequency: 10}, |
|
|
|
|
{Id: 3, Title: "alert rule 3", Interval: "10s", Frequency: 10}, |
|
|
|
|
{Id: 4, Title: "alert rule 4", Interval: "10s", Frequency: 5}, |
|
|
|
|
{Id: 5, Title: "alert rule 5", Interval: "10s", Frequency: 5}, |
|
|
|
|
{Id: 6, Title: "alert rule 6", Interval: "10s", Frequency: 1}, |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func (s *Scheduler) updateJobs() { |
|
|
|
|
log.Info("Scheduler:updateJobs()") |
|
|
|
|
log.Info("Scheduler: UpdateJobs()") |
|
|
|
|
|
|
|
|
|
jobs := make([]*AlertJob, 0) |
|
|
|
|
jobs = append(jobs, &AlertJob{ |
|
|
|
|
name: "ID_1_Each 10s", |
|
|
|
|
frequency: 10, |
|
|
|
|
offset: 1, |
|
|
|
|
}) |
|
|
|
|
jobs = append(jobs, &AlertJob{ |
|
|
|
|
name: "ID_2_Each 10s", |
|
|
|
|
frequency: 10, |
|
|
|
|
offset: 2, |
|
|
|
|
}) |
|
|
|
|
jobs = append(jobs, &AlertJob{ |
|
|
|
|
name: "ID_3_Each 10s", |
|
|
|
|
frequency: 10, |
|
|
|
|
offset: 3, |
|
|
|
|
}) |
|
|
|
|
|
|
|
|
|
jobs = append(jobs, &AlertJob{ |
|
|
|
|
name: "ID_4_Each 5s", |
|
|
|
|
frequency: 5, |
|
|
|
|
}) |
|
|
|
|
rules := s.getAlertRules() |
|
|
|
|
|
|
|
|
|
for i := s.serverPosition - 1; i < len(rules); i = i + s.clusterSize { |
|
|
|
|
rule := rules[i] |
|
|
|
|
jobs = append(jobs, &AlertJob{ |
|
|
|
|
name: rule.Title, |
|
|
|
|
frequency: rule.Frequency, |
|
|
|
|
rule: rule, |
|
|
|
|
offset: int64(len(jobs)), |
|
|
|
|
}) |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
log.Debug("Scheduler: Selected %d jobs", len(jobs)) |
|
|
|
|
|
|
|
|
|
s.jobs = jobs |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
func (s *Scheduler) queueJobs() { |
|
|
|
|
log.Info("Scheduler:queueJobs()") |
|
|
|
|
|
|
|
|
|
now := time.Now().Unix() |
|
|
|
|
|
|
|
|
|
for _, job := range s.jobs { |
|
|
|
|
@ -104,6 +127,7 @@ type AlertJob struct { |
|
|
|
|
frequency int64 |
|
|
|
|
offset int64 |
|
|
|
|
delay bool |
|
|
|
|
rule m.AlertRule |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
type RuleReader interface { |
|
|
|
|
|