Alerting: Add additional customisation to ngalert MS Teams notifier (#46372)

Makes the Title and Section Title of the Teams message customisable.
Closes #46366
This commit is contained in:
cianooooo 2022-04-27 18:03:15 +01:00 committed by GitHub
parent ebfb70dc12
commit e8f4b58a8b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 51 additions and 22 deletions

View File

@ -562,6 +562,21 @@ func GetAvailableNotifiers() []*alerting.NotifierPlugin {
PropertyName: "url",
Required: true,
},
{
Label: "Title",
Element: alerting.ElementTypeInput,
InputType: alerting.InputTypeText,
Description: "Templated title of the Teams message.",
PropertyName: "title",
Placeholder: `{{ template "default.title" . }}`,
},
{
Label: "Section Title",
Element: alerting.ElementTypeInput,
InputType: alerting.InputTypeText,
Description: "Section title for the Teams message. Leave blank for none.",
PropertyName: "sectiontitle",
},
{ // New in 8.0.
Label: "Message",
Element: alerting.ElementTypeTextArea,

View File

@ -17,17 +17,21 @@ import (
// alert notifications to Microsoft teams.
type TeamsNotifier struct {
*Base
URL string
Message string
tmpl *template.Template
log log.Logger
ns notifications.WebhookSender
URL string
Message string
Title string
SectionTitle string
tmpl *template.Template
log log.Logger
ns notifications.WebhookSender
}
type TeamsConfig struct {
*NotificationChannelConfig
URL string
Message string
URL string
Message string
Title string
SectionTitle string
}
func TeamsFactory(fc FactoryConfig) (NotificationChannel, error) {
@ -50,6 +54,8 @@ func NewTeamsConfig(config *NotificationChannelConfig) (*TeamsConfig, error) {
NotificationChannelConfig: config,
URL: URL,
Message: config.Settings.Get("message").MustString(`{{ template "teams.default.message" .}}`),
Title: config.Settings.Get("title").MustString(DefaultMessageTitleEmbed),
SectionTitle: config.Settings.Get("sectiontitle").MustString(""),
}, nil
}
@ -63,11 +69,13 @@ func NewTeamsNotifier(config *TeamsConfig, ns notifications.WebhookSender, t *te
DisableResolveMessage: config.DisableResolveMessage,
Settings: config.Settings,
}),
URL: config.URL,
Message: config.Message,
log: log.New("alerting.notifier.teams"),
ns: ns,
tmpl: t,
URL: config.URL,
Message: config.Message,
Title: config.Title,
SectionTitle: config.SectionTitle,
log: log.New("alerting.notifier.teams"),
ns: ns,
tmpl: t,
}
}
@ -78,7 +86,7 @@ func (tn *TeamsNotifier) Notify(ctx context.Context, as ...*types.Alert) (bool,
ruleURL := joinUrlPath(tn.tmpl.ExternalURL.String(), "/alerting/list", tn.log)
title := tmpl(DefaultMessageTitleEmbed)
title := tmpl(tn.Title)
body := map[string]interface{}{
"@type": "MessageCard",
"@context": "http://schema.org/extensions",
@ -89,7 +97,7 @@ func (tn *TeamsNotifier) Notify(ctx context.Context, as ...*types.Alert) (bool,
"themeColor": getAlertStatusColor(types.Alerts(as...).Status()),
"sections": []map[string]interface{}{
{
"title": "Details",
"title": tmpl(tn.SectionTitle),
"text": tmpl(tn.Message),
},
},

View File

@ -48,7 +48,7 @@ func TestTeamsNotifier(t *testing.T) {
"themeColor": "#D63232",
"sections": []map[string]interface{}{
{
"title": "Details",
"title": "",
"text": "**Firing**\n\nValue: [no value]\nLabels:\n - alertname = alert1\n - lbl1 = val1\nAnnotations:\n - ann1 = annv1\nSilence: http://localhost/alerting/silence/new?alertmanager=grafana&matcher=alertname%3Dalert1&matcher=lbl1%3Dval1\nDashboard: http://localhost/d/abcd\nPanel: http://localhost/d/abcd?viewPanel=efgh\n",
},
},
@ -66,6 +66,8 @@ func TestTeamsNotifier(t *testing.T) {
name: "Custom config with multiple alerts",
settings: `{
"url": "http://localhost",
"title": "{{ .CommonLabels.alertname }}",
"sectiontitle": "Details",
"message": "{{ len .Alerts.Firing }} alerts are firing, {{ len .Alerts.Resolved }} are resolved"
}`,
alerts: []*types.Alert{
@ -84,8 +86,8 @@ func TestTeamsNotifier(t *testing.T) {
expMsg: map[string]interface{}{
"@type": "MessageCard",
"@context": "http://schema.org/extensions",
"summary": "[FIRING:2] ",
"title": "[FIRING:2] ",
"summary": "alert1",
"title": "alert1",
"themeColor": "#D63232",
"sections": []map[string]interface{}{
{
@ -107,6 +109,8 @@ func TestTeamsNotifier(t *testing.T) {
name: "Missing field in template",
settings: `{
"url": "http://localhost",
"title": "{{ .CommonLabels.alertname }}",
"sectiontitle": "Details",
"message": "I'm a custom template {{ .NotAField }} bad template"
}`,
alerts: []*types.Alert{
@ -125,8 +129,8 @@ func TestTeamsNotifier(t *testing.T) {
expMsg: map[string]interface{}{
"@type": "MessageCard",
"@context": "http://schema.org/extensions",
"summary": "[FIRING:2] ",
"title": "[FIRING:2] ",
"summary": "alert1",
"title": "alert1",
"themeColor": "#D63232",
"sections": []map[string]interface{}{
{
@ -148,6 +152,8 @@ func TestTeamsNotifier(t *testing.T) {
name: "Invalid template",
settings: `{
"url": "http://localhost",
"title": "{{ .CommonLabels.alertname }}",
"sectiontitle": "Details",
"message": "I'm a custom template {{ {.NotAField }} bad template"
}`,
alerts: []*types.Alert{
@ -166,8 +172,8 @@ func TestTeamsNotifier(t *testing.T) {
expMsg: map[string]interface{}{
"@type": "MessageCard",
"@context": "http://schema.org/extensions",
"summary": "[FIRING:2] ",
"title": "[FIRING:2] ",
"summary": "alert1",
"title": "alert1",
"themeColor": "#D63232",
"sections": []map[string]interface{}{
{

View File

@ -2226,7 +2226,7 @@ var expNonEmailNotifications = map[string][]string{
"sections": [
{
"text": "**Firing**\n\nValue: [ var='A' labels={} value=1 ]\nLabels:\n - alertname = TeamsAlert\nAnnotations:\nSource: http://localhost:3000/alerting/grafana/UID_TeamsAlert/view\nSilence: http://localhost:3000/alerting/silence/new?alertmanager=grafana&matcher=alertname%3DTeamsAlert\n",
"title": "Details"
"title": ""
}
],
"summary": "[FIRING:1] TeamsAlert ",