fix(alerting): Use reflection to set invalid providers to nil instead of re-validating on every alert trigger/resolve

This commit is contained in:
TwiN 2022-12-15 20:54:38 -05:00
parent a5f135c675
commit dfcea93080
4 changed files with 22 additions and 7 deletions

View File

@ -1,6 +1,9 @@
package alerting package alerting
import ( import (
"fmt"
"reflect"
"github.com/TwiN/gatus/v5/alerting/alert" "github.com/TwiN/gatus/v5/alerting/alert"
"github.com/TwiN/gatus/v5/alerting/provider" "github.com/TwiN/gatus/v5/alerting/provider"
"github.com/TwiN/gatus/v5/alerting/provider/custom" "github.com/TwiN/gatus/v5/alerting/provider/custom"
@ -154,3 +157,17 @@ func (config Config) GetAlertingProviderByAlertType(alertType alert.Type) provid
} }
return nil return nil
} }
// SetAlertingProviderToNil Sets an alerting provider to nil to avoid having to revalidate it every time an
// alert of its corresponding type is sent.
func (config *Config) SetAlertingProviderToNil(p provider.AlertProvider) {
fmt.Println(config.GitHub)
entityType := reflect.TypeOf(config).Elem()
for i := 0; i < entityType.NumField(); i++ {
field := entityType.Field(i)
if field.Type == reflect.TypeOf(p) {
fmt.Println("Setting", field.Name, "to nil")
reflect.ValueOf(config).Elem().Field(i).Set(reflect.Zero(field.Type))
}
}
}

View File

@ -323,6 +323,7 @@ func validateAlertingConfig(alertingConfig *alerting.Config, endpoints []*core.E
} else { } else {
log.Printf("[config][validateAlertingConfig] Ignoring provider=%s because configuration is invalid", alertType) log.Printf("[config][validateAlertingConfig] Ignoring provider=%s because configuration is invalid", alertType)
invalidProviders = append(invalidProviders, alertType) invalidProviders = append(invalidProviders, alertType)
alertingConfig.SetAlertingProviderToNil(alertProvider)
} }
} else { } else {
invalidProviders = append(invalidProviders, alertType) invalidProviders = append(invalidProviders, alertType)

View File

@ -980,11 +980,8 @@ endpoints:
if config.Alerting == nil { if config.Alerting == nil {
t.Fatal("config.Alerting shouldn't have been nil") t.Fatal("config.Alerting shouldn't have been nil")
} }
if config.Alerting.PagerDuty == nil { if config.Alerting.PagerDuty != nil {
t.Fatal("PagerDuty alerting config shouldn't have been nil") t.Fatal("PagerDuty alerting config should've been set to nil, because its IsValid() method returned false and therefore alerting.Config.SetAlertingProviderToNil() should've been called")
}
if config.Alerting.PagerDuty.IsValid() {
t.Fatal("PagerDuty alerting config should've been invalid")
} }
} }

View File

@ -36,7 +36,7 @@ func handleAlertsToTrigger(endpoint *core.Endpoint, result *core.Result, alertin
continue continue
} }
alertProvider := alertingConfig.GetAlertingProviderByAlertType(endpointAlert.Type) alertProvider := alertingConfig.GetAlertingProviderByAlertType(endpointAlert.Type)
if alertProvider != nil && alertProvider.IsValid() { if alertProvider != nil {
log.Printf("[watchdog][handleAlertsToTrigger] Sending %s alert because alert for endpoint=%s with description='%s' has been TRIGGERED", endpointAlert.Type, endpoint.Name, endpointAlert.GetDescription()) log.Printf("[watchdog][handleAlertsToTrigger] Sending %s alert because alert for endpoint=%s with description='%s' has been TRIGGERED", endpointAlert.Type, endpoint.Name, endpointAlert.GetDescription())
var err error var err error
if os.Getenv("MOCK_ALERT_PROVIDER") == "true" { if os.Getenv("MOCK_ALERT_PROVIDER") == "true" {
@ -70,7 +70,7 @@ func handleAlertsToResolve(endpoint *core.Endpoint, result *core.Result, alertin
continue continue
} }
alertProvider := alertingConfig.GetAlertingProviderByAlertType(endpointAlert.Type) alertProvider := alertingConfig.GetAlertingProviderByAlertType(endpointAlert.Type)
if alertProvider != nil && alertProvider.IsValid() { if alertProvider != nil {
log.Printf("[watchdog][handleAlertsToResolve] Sending %s alert because alert for endpoint=%s with description='%s' has been RESOLVED", endpointAlert.Type, endpoint.Name, endpointAlert.GetDescription()) log.Printf("[watchdog][handleAlertsToResolve] Sending %s alert because alert for endpoint=%s with description='%s' has been RESOLVED", endpointAlert.Type, endpoint.Name, endpointAlert.GetDescription())
err := alertProvider.Send(endpoint, endpointAlert, result, true) err := alertProvider.Send(endpoint, endpointAlert, result, true)
if err != nil { if err != nil {