mirror of
https://github.com/grafana/grafana.git
synced 2025-02-25 18:55:37 -06:00
Merge pull request #6996 from bergquist/pause_all_alerts
Pause all alerts
This commit is contained in:
@@ -259,9 +259,10 @@ func NotificationTest(c *middleware.Context, dto dtos.NotificationTestCommand) R
|
|||||||
|
|
||||||
//POST /api/alerts/:alertId/pause
|
//POST /api/alerts/:alertId/pause
|
||||||
func PauseAlert(c *middleware.Context, dto dtos.PauseAlertCommand) Response {
|
func PauseAlert(c *middleware.Context, dto dtos.PauseAlertCommand) Response {
|
||||||
|
alertId := c.ParamsInt64("alertId")
|
||||||
cmd := models.PauseAlertCommand{
|
cmd := models.PauseAlertCommand{
|
||||||
OrgId: c.OrgId,
|
OrgId: c.OrgId,
|
||||||
AlertId: c.ParamsInt64("alertId"),
|
AlertIds: []int64{alertId},
|
||||||
Paused: dto.Paused,
|
Paused: dto.Paused,
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -277,10 +278,36 @@ func PauseAlert(c *middleware.Context, dto dtos.PauseAlertCommand) Response {
|
|||||||
}
|
}
|
||||||
|
|
||||||
result := map[string]interface{}{
|
result := map[string]interface{}{
|
||||||
"alertId": cmd.AlertId,
|
"alertId": alertId,
|
||||||
"state": response,
|
"state": response,
|
||||||
"message": "alert " + pausedState,
|
"message": "alert " + pausedState,
|
||||||
}
|
}
|
||||||
|
|
||||||
return Json(200, result)
|
return Json(200, result)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//POST /api/admin/pause-all-alerts
|
||||||
|
func PauseAllAlerts(c *middleware.Context, dto dtos.PauseAllAlertsCommand) Response {
|
||||||
|
updateCmd := models.PauseAllAlertCommand{
|
||||||
|
Paused: dto.Paused,
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := bus.Dispatch(&updateCmd); err != nil {
|
||||||
|
return ApiError(500, "Failed to pause alerts", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
var response models.AlertStateType = models.AlertStatePending
|
||||||
|
pausedState := "un paused"
|
||||||
|
if updateCmd.Paused {
|
||||||
|
response = models.AlertStatePaused
|
||||||
|
pausedState = "paused"
|
||||||
|
}
|
||||||
|
|
||||||
|
result := map[string]interface{}{
|
||||||
|
"state": response,
|
||||||
|
"message": "alert " + pausedState,
|
||||||
|
"alertsAffected": updateCmd.ResultCount,
|
||||||
|
}
|
||||||
|
|
||||||
|
return Json(200, result)
|
||||||
|
}
|
||||||
|
|||||||
@@ -289,6 +289,7 @@ func Register(r *macaron.Macaron) {
|
|||||||
r.Get("/users/:id/quotas", wrap(GetUserQuotas))
|
r.Get("/users/:id/quotas", wrap(GetUserQuotas))
|
||||||
r.Put("/users/:id/quotas/:target", bind(m.UpdateUserQuotaCmd{}), wrap(UpdateUserQuota))
|
r.Put("/users/:id/quotas/:target", bind(m.UpdateUserQuotaCmd{}), wrap(UpdateUserQuota))
|
||||||
r.Get("/stats", AdminGetStats)
|
r.Get("/stats", AdminGetStats)
|
||||||
|
r.Post("/pause-all-alerts", bind(dtos.PauseAllAlertsCommand{}), wrap(PauseAllAlerts))
|
||||||
}, reqGrafanaAdmin)
|
}, reqGrafanaAdmin)
|
||||||
|
|
||||||
// rendering
|
// rendering
|
||||||
|
|||||||
@@ -64,3 +64,7 @@ type PauseAlertCommand struct {
|
|||||||
AlertId int64 `json:"alertId"`
|
AlertId int64 `json:"alertId"`
|
||||||
Paused bool `json:"paused"`
|
Paused bool `json:"paused"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type PauseAllAlertsCommand struct {
|
||||||
|
Paused bool `json:"paused"`
|
||||||
|
}
|
||||||
|
|||||||
@@ -3,6 +3,8 @@ package models
|
|||||||
import (
|
import (
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
|
"fmt"
|
||||||
|
|
||||||
"github.com/grafana/grafana/pkg/components/simplejson"
|
"github.com/grafana/grafana/pkg/components/simplejson"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -31,6 +33,10 @@ const (
|
|||||||
ExecutionErrorKeepState ExecutionErrorOption = "keep_state"
|
ExecutionErrorKeepState ExecutionErrorOption = "keep_state"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
var (
|
||||||
|
ErrCannotChangeStateOnPausedAlert error = fmt.Errorf("Cannot change state on pause alert")
|
||||||
|
)
|
||||||
|
|
||||||
func (s AlertStateType) IsValid() bool {
|
func (s AlertStateType) IsValid() bool {
|
||||||
return s == AlertStateOK || s == AlertStateNoData || s == AlertStatePaused || s == AlertStatePending
|
return s == AlertStateOK || s == AlertStateNoData || s == AlertStatePaused || s == AlertStatePending
|
||||||
}
|
}
|
||||||
@@ -133,7 +139,13 @@ type SaveAlertsCommand struct {
|
|||||||
|
|
||||||
type PauseAlertCommand struct {
|
type PauseAlertCommand struct {
|
||||||
OrgId int64
|
OrgId int64
|
||||||
AlertId int64
|
AlertIds []int64
|
||||||
|
ResultCount int64
|
||||||
|
Paused bool
|
||||||
|
}
|
||||||
|
|
||||||
|
type PauseAllAlertCommand struct {
|
||||||
|
ResultCount int64
|
||||||
Paused bool
|
Paused bool
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -86,6 +86,10 @@ func (handler *DefaultResultHandler) Handle(evalContext *EvalContext) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if err := bus.Dispatch(cmd); err != nil {
|
if err := bus.Dispatch(cmd); err != nil {
|
||||||
|
if err == m.ErrCannotChangeStateOnPausedAlert {
|
||||||
|
handler.log.Error("Cannot change state on alert thats pause", "error", err)
|
||||||
|
return err
|
||||||
|
}
|
||||||
handler.log.Error("Failed to save state", "error", err)
|
handler.log.Error("Failed to save state", "error", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ package sqlstore
|
|||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/go-xorm/xorm"
|
"github.com/go-xorm/xorm"
|
||||||
@@ -18,7 +19,8 @@ func init() {
|
|||||||
bus.AddHandler("sql", GetAllAlertQueryHandler)
|
bus.AddHandler("sql", GetAllAlertQueryHandler)
|
||||||
bus.AddHandler("sql", SetAlertState)
|
bus.AddHandler("sql", SetAlertState)
|
||||||
bus.AddHandler("sql", GetAlertStatesForDashboard)
|
bus.AddHandler("sql", GetAlertStatesForDashboard)
|
||||||
bus.AddHandler("sql", PauseAlertRule)
|
bus.AddHandler("sql", PauseAlert)
|
||||||
|
bus.AddHandler("sql", PauseAllAlerts)
|
||||||
}
|
}
|
||||||
|
|
||||||
func GetAlertById(query *m.GetAlertByIdQuery) error {
|
func GetAlertById(query *m.GetAlertByIdQuery) error {
|
||||||
@@ -228,6 +230,10 @@ func SetAlertState(cmd *m.SetAlertStateCommand) error {
|
|||||||
return fmt.Errorf("Could not find alert")
|
return fmt.Errorf("Could not find alert")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if alert.State == m.AlertStatePaused {
|
||||||
|
return m.ErrCannotChangeStateOnPausedAlert
|
||||||
|
}
|
||||||
|
|
||||||
alert.State = cmd.State
|
alert.State = cmd.State
|
||||||
alert.StateChanges += 1
|
alert.StateChanges += 1
|
||||||
alert.NewStateDate = time.Now()
|
alert.NewStateDate = time.Now()
|
||||||
@@ -244,27 +250,50 @@ func SetAlertState(cmd *m.SetAlertStateCommand) error {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
func PauseAlertRule(cmd *m.PauseAlertCommand) error {
|
func PauseAlert(cmd *m.PauseAlertCommand) error {
|
||||||
return inTransaction(func(sess *xorm.Session) error {
|
return inTransaction(func(sess *xorm.Session) error {
|
||||||
alert := m.Alert{}
|
if len(cmd.AlertIds) == 0 {
|
||||||
|
return fmt.Errorf("command contains no alertids")
|
||||||
|
}
|
||||||
|
|
||||||
has, err := x.Where("id = ? AND org_id=?", cmd.AlertId, cmd.OrgId).Get(&alert)
|
var buffer bytes.Buffer
|
||||||
|
params := make([]interface{}, 0)
|
||||||
|
|
||||||
|
buffer.WriteString(`UPDATE alert SET state = ?`)
|
||||||
|
if cmd.Paused {
|
||||||
|
params = append(params, string(m.AlertStatePaused))
|
||||||
|
} else {
|
||||||
|
params = append(params, string(m.AlertStatePending))
|
||||||
|
}
|
||||||
|
|
||||||
|
buffer.WriteString(` WHERE id IN (?` + strings.Repeat(",?", len(cmd.AlertIds)-1) + `)`)
|
||||||
|
for _, v := range cmd.AlertIds {
|
||||||
|
params = append(params, v)
|
||||||
|
}
|
||||||
|
|
||||||
|
res, err := sess.Exec(buffer.String(), params...)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
} else if !has {
|
|
||||||
return fmt.Errorf("Could not find alert")
|
|
||||||
}
|
}
|
||||||
|
cmd.ResultCount, _ = res.RowsAffected()
|
||||||
|
return nil
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
var newState m.AlertStateType
|
func PauseAllAlerts(cmd *m.PauseAllAlertCommand) error {
|
||||||
|
return inTransaction(func(sess *xorm.Session) error {
|
||||||
|
var newState string
|
||||||
if cmd.Paused {
|
if cmd.Paused {
|
||||||
newState = m.AlertStatePaused
|
newState = string(m.AlertStatePaused)
|
||||||
} else {
|
} else {
|
||||||
newState = m.AlertStatePending
|
newState = string(m.AlertStatePending)
|
||||||
}
|
}
|
||||||
alert.State = newState
|
|
||||||
|
|
||||||
sess.Id(alert.Id).Update(&alert)
|
res, err := sess.Exec(`UPDATE alert SET state = ?`, newState)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
cmd.ResultCount, _ = res.RowsAffected()
|
||||||
return nil
|
return nil
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,18 +0,0 @@
|
|||||||
package sqlstore
|
|
||||||
|
|
||||||
import (
|
|
||||||
"testing"
|
|
||||||
|
|
||||||
// m "github.com/grafana/grafana/pkg/models"
|
|
||||||
. "github.com/smartystreets/goconvey/convey"
|
|
||||||
)
|
|
||||||
|
|
||||||
func TestAlertingHeartbeatDataAccess(t *testing.T) {
|
|
||||||
|
|
||||||
Convey("Testing Alerting data access", t, func() {
|
|
||||||
InitTestDB(t)
|
|
||||||
//send heartbeat from server 1
|
|
||||||
//send heartbeat from server 2
|
|
||||||
|
|
||||||
})
|
|
||||||
}
|
|
||||||
@@ -39,6 +39,37 @@ func TestAlertingDataAccess(t *testing.T) {
|
|||||||
So(err, ShouldBeNil)
|
So(err, ShouldBeNil)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
Convey("Can set new states", func() {
|
||||||
|
Convey("new state ok", func() {
|
||||||
|
cmd := &m.SetAlertStateCommand{
|
||||||
|
AlertId: 1,
|
||||||
|
State: m.AlertStateOK,
|
||||||
|
}
|
||||||
|
|
||||||
|
err = SetAlertState(cmd)
|
||||||
|
So(err, ShouldBeNil)
|
||||||
|
})
|
||||||
|
|
||||||
|
Convey("can pause alert", func() {
|
||||||
|
cmd := &m.PauseAllAlertCommand{
|
||||||
|
Paused: true,
|
||||||
|
}
|
||||||
|
|
||||||
|
err = PauseAllAlerts(cmd)
|
||||||
|
So(err, ShouldBeNil)
|
||||||
|
|
||||||
|
Convey("cannot updated paused alert", func() {
|
||||||
|
cmd := &m.SetAlertStateCommand{
|
||||||
|
AlertId: 1,
|
||||||
|
State: m.AlertStateOK,
|
||||||
|
}
|
||||||
|
|
||||||
|
err = SetAlertState(cmd)
|
||||||
|
So(err, ShouldNotBeNil)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
Convey("Can read properties", func() {
|
Convey("Can read properties", func() {
|
||||||
alertQuery := m.GetAlertsQuery{DashboardId: testDash.Id, PanelId: 1, OrgId: 1}
|
alertQuery := m.GetAlertsQuery{DashboardId: testDash.Id, PanelId: 1, OrgId: 1}
|
||||||
err2 := HandleAlertsQuery(&alertQuery)
|
err2 := HandleAlertsQuery(&alertQuery)
|
||||||
|
|||||||
Reference in New Issue
Block a user