mirror of
https://github.com/grafana/grafana.git
synced 2025-02-25 18:55:37 -06:00
Migration: Edit notification channel (#25980)
* implement edit page * connectWithCleanup * remove angular related code * use loadingindicator * use the correct loading component * handle secureFields * fixed implementation of secure fields * Keep secureFields after rerendering the form * CollapsableSection and Page refactor * use checkbox instead of switch * fix comment * add cursor to section * Fixed issues after PR review * Fix issue with some settings being undefined * new reducer and start with test * algorithm to migrate secure fields * UX: Minor UI Tweaks * Added field around checkboxes, and missing required field * fixed test * tests for util * minor tweaks and changes * define as records * fix typ error * forward invalid to textarea and inputcontrol * merge formdata and redux data in test * fix issue with creating channel * do not figure out securefields in migration Co-authored-by: Torkel Ödegaard <torkel@grafana.com>
This commit is contained in:
@@ -23,14 +23,13 @@ var newImageUploaderProvider = func() (imguploader.ImageUploader, error) {
|
||||
|
||||
// NotifierPlugin holds meta information about a notifier.
|
||||
type NotifierPlugin struct {
|
||||
Type string `json:"type"`
|
||||
Name string `json:"name"`
|
||||
Heading string `json:"heading"`
|
||||
Description string `json:"description"`
|
||||
Info string `json:"info"`
|
||||
OptionsTemplate string `json:"optionsTemplate"`
|
||||
Factory NotifierFactory `json:"-"`
|
||||
Options []NotifierOption `json:"options"`
|
||||
Type string `json:"type"`
|
||||
Name string `json:"name"`
|
||||
Heading string `json:"heading"`
|
||||
Description string `json:"description"`
|
||||
Info string `json:"info"`
|
||||
Factory NotifierFactory `json:"-"`
|
||||
Options []NotifierOption `json:"options"`
|
||||
}
|
||||
|
||||
// NotifierOption holds information about options specific for the NotifierPlugin.
|
||||
@@ -45,6 +44,7 @@ type NotifierOption struct {
|
||||
ShowWhen ShowWhen `json:"showWhen"`
|
||||
Required bool `json:"required"`
|
||||
ValidationRule string `json:"validationRule"`
|
||||
Secure bool `json:"secure"`
|
||||
}
|
||||
|
||||
// InputType is the type of input that can be rendered in the frontend.
|
||||
@@ -65,8 +65,8 @@ const (
|
||||
ElementTypeInput = "input"
|
||||
// ElementTypeSelect will render a select
|
||||
ElementTypeSelect = "select"
|
||||
// ElementTypeSwitch will render a switch
|
||||
ElementTypeSwitch = "switch"
|
||||
// ElementTypeCheckbox will render a checkbox
|
||||
ElementTypeCheckbox = "checkbox"
|
||||
// ElementTypeTextArea will render a textarea
|
||||
ElementTypeTextArea = "textarea"
|
||||
)
|
||||
|
||||
@@ -20,36 +20,6 @@ func init() {
|
||||
Description: "Sends alert to Prometheus Alertmanager",
|
||||
Heading: "Alertmanager settings",
|
||||
Factory: NewAlertmanagerNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Alertmanager settings</h3>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-10">Url(s)</span>
|
||||
<input type="text" required class="gf-form-input max-width-30" ng-model="ctrl.model.settings.url" placeholder="http://localhost:9093"></input>
|
||||
<info-popover mode="right-absolute">
|
||||
As specified in Alertmanager documentation, do not specify a load balancer here. Enter all your Alertmanager URLs comma-separated.
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-10">Basic Auth User</span>
|
||||
<input type="text" class="gf-form-input max-width-30" ng-model="ctrl.model.settings.basicAuthUser" placeholder=""></input>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-10">Basic Auth Password</span>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.basicAuthPassword">
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-init="ctrl.model.secureSettings.basicAuthPassword = ctrl.model.settings.basicAuthPassword || null; ctrl.model.settings.basicAuthPassword = null;"
|
||||
ng-model="ctrl.model.secureSettings.basicAuthPassword"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.basicAuthPassword">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.basicAuthPassword = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Url",
|
||||
@@ -71,6 +41,7 @@ func init() {
|
||||
Element: alerting.ElementTypeInput,
|
||||
InputType: alerting.InputTypePassword,
|
||||
PropertyName: "basicAuthPassword",
|
||||
Secure: true,
|
||||
},
|
||||
},
|
||||
})
|
||||
|
||||
@@ -12,26 +12,14 @@ import (
|
||||
)
|
||||
|
||||
const defaultDingdingMsgType = "link"
|
||||
const dingdingOptionsTemplate = `
|
||||
<h3 class="page-heading">DingDing settings</h3>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">Url</span>
|
||||
<input type="text" required class="gf-form-input max-width-70" ng-model="ctrl.model.settings.url" placeholder="https://oapi.dingtalk.com/robot/send?access_token=xxxxxxxxx"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">MessageType</span>
|
||||
<select class="gf-form-input max-width-14" ng-model="ctrl.model.settings.msgType" ng-options="s for s in ['link','actionCard']" ng-init="ctrl.model.settings.msgType=ctrl.model.settings.msgType || '` + defaultDingdingMsgType + `'"></select>
|
||||
</div>
|
||||
`
|
||||
|
||||
func init() {
|
||||
alerting.RegisterNotifier(&alerting.NotifierPlugin{
|
||||
Type: "dingding",
|
||||
Name: "DingDing",
|
||||
Description: "Sends HTTP POST request to DingDing",
|
||||
Heading: "DingDing settings",
|
||||
Factory: newDingDingNotifier,
|
||||
OptionsTemplate: dingdingOptionsTemplate,
|
||||
Type: "dingding",
|
||||
Name: "DingDing",
|
||||
Description: "Sends HTTP POST request to DingDing",
|
||||
Heading: "DingDing settings",
|
||||
Factory: newDingDingNotifier,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Url",
|
||||
|
||||
@@ -23,24 +23,6 @@ func init() {
|
||||
Description: "Sends notifications to Discord",
|
||||
Factory: newDiscordNotifier,
|
||||
Heading: "Discord settings",
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Discord settings</h3>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-10">Message Content</span>
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.content"
|
||||
data-placement="right">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
Mention a group using @ or a user using <@ID> when notifying in a channel
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-10">Webhook URL</span>
|
||||
<input type="text" required class="gf-form-input max-width-30" ng-model="ctrl.model.settings.url" placeholder="Discord webhook URL"></input>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Message Content",
|
||||
|
||||
@@ -19,32 +19,11 @@ func init() {
|
||||
Description: "Sends notifications using Grafana server configured SMTP settings",
|
||||
Factory: NewEmailNotifier,
|
||||
Heading: "Email settings",
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Email settings</h3>
|
||||
<div class="gf-form">
|
||||
<gf-form-switch
|
||||
class="gf-form"
|
||||
label="Single email"
|
||||
label-class="width-8"
|
||||
checked="ctrl.model.settings.singleEmail"
|
||||
tooltip="Send a single email to all recipients">
|
||||
</gf-form-switch>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<label class="gf-form-label width-8">
|
||||
Addresses
|
||||
</label>
|
||||
<textarea rows="7" class="gf-form-input width-27" required ng-model="ctrl.model.settings.addresses"></textarea>
|
||||
</div>
|
||||
<div class="gf-form offset-width-8">
|
||||
<span>You can enter multiple email addresses using a ";" separator</span>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Single email",
|
||||
Description: "Send a single email to all recipients",
|
||||
Element: alerting.ElementTypeSwitch,
|
||||
Element: alerting.ElementTypeCheckbox,
|
||||
PropertyName: "singleEmail",
|
||||
},
|
||||
{
|
||||
|
||||
@@ -19,13 +19,6 @@ func init() {
|
||||
Description: "Sends notifications to Google Hangouts Chat via webhooks based on the official JSON message format",
|
||||
Factory: newGoogleChatNotifier,
|
||||
Heading: "Google Hangouts Chat settings",
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Google Hangouts Chat settings</h3>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-6">Url</span>
|
||||
<input type="text" required class="gf-form-input max-width-30" ng-model="ctrl.model.settings.url" placeholder="Google Hangouts Chat incoming webhook url"></input>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Url",
|
||||
|
||||
@@ -20,25 +20,6 @@ func init() {
|
||||
Description: "Sends notifications uto a HipChat Room",
|
||||
Heading: "HipChat settings",
|
||||
Factory: NewHipChatNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">HipChat settings</h3>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Hip Chat Url</span>
|
||||
<input type="text" required class="gf-form-input max-width-30" ng-model="ctrl.model.settings.url" placeholder="HipChat URL (ex https://grafana.hipchat.com)"></input>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">API Key</span>
|
||||
<input type="text" required class="gf-form-input max-width-30" ng-model="ctrl.model.settings.apikey" placeholder="HipChat API Key"></input>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Room ID</span>
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.roomid"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Hip Chat Url",
|
||||
|
||||
@@ -19,17 +19,6 @@ func init() {
|
||||
Description: "Sends notifications to Kafka Rest Proxy",
|
||||
Heading: "Kafka settings",
|
||||
Factory: NewKafkaNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Kafka settings</h3>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-14">Kafka REST Proxy</span>
|
||||
<input type="text" required class="gf-form-input max-width-22" ng-model="ctrl.model.settings.kafkaRestProxy" placeholder="http://localhost:8082"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-14">Topic</span>
|
||||
<input type="text" required class="gf-form-input max-width-22" ng-model="ctrl.model.settings.kafkaTopic" placeholder="topic1"></input>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Kafka REST Proxy",
|
||||
|
||||
@@ -17,25 +17,6 @@ func init() {
|
||||
Description: "Send notifications to LINE notify",
|
||||
Heading: "LINE notify settings",
|
||||
Factory: NewLINENotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">LINE notify settings</h3>
|
||||
<div class="gf-form">
|
||||
<label class="gf-form-label max-width-14">Token</label>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.token">
|
||||
<input type="text"
|
||||
required
|
||||
class="gf-form-input max-width-22"
|
||||
ng-init="ctrl.model.secureSettings.token = ctrl.model.settings.token || null; ctrl.model.settings.token = null;"
|
||||
ng-model="ctrl.model.secureSettings.token"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.token">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.token = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Token",
|
||||
@@ -44,6 +25,7 @@ func init() {
|
||||
Placeholder: "LINE notify token key",
|
||||
PropertyName: "token",
|
||||
Required: true,
|
||||
Secure: true,
|
||||
}},
|
||||
})
|
||||
}
|
||||
|
||||
@@ -18,48 +18,6 @@ func init() {
|
||||
Description: "Sends notifications to OpsGenie",
|
||||
Heading: "OpsGenie settings",
|
||||
Factory: NewOpsGenieNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">OpsGenie settings</h3>
|
||||
<div class="gf-form">
|
||||
<label class="gf-form-label max-width-14">API Key</label>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.apiKey">
|
||||
<input type="text"
|
||||
required
|
||||
class="gf-form-input max-width-22"
|
||||
ng-init="ctrl.model.secureSettings.apiKey = ctrl.model.settings.apiKey || null; ctrl.model.settings.apiKey = null;"
|
||||
ng-model="ctrl.model.secureSettings.apiKey"
|
||||
placeholder="OpsGenie API Key"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.apiKey">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.apiKey = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-14">Alert API Url</span>
|
||||
<input type="text" required class="gf-form-input max-width-22" ng-model="ctrl.model.settings.apiUrl" placeholder="https://api.opsgenie.com/v2/alerts"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<gf-form-switch
|
||||
class="gf-form"
|
||||
label="Auto close incidents"
|
||||
label-class="width-14"
|
||||
checked="ctrl.model.settings.autoClose"
|
||||
tooltip="Automatically close alerts in OpsGenie once the alert goes back to ok.">
|
||||
</gf-form-switch>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<gf-form-switch
|
||||
class="gf-form"
|
||||
label="Override priority"
|
||||
label-class="width-14"
|
||||
checked="ctrl.model.settings.overridePriority"
|
||||
tooltip="Allow the alert priority to be set using the og_priority tag">
|
||||
</gf-form-switch>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "API Key",
|
||||
@@ -68,6 +26,7 @@ func init() {
|
||||
Placeholder: "OpsGenie API Key",
|
||||
PropertyName: "apiKey",
|
||||
Required: true,
|
||||
Secure: true,
|
||||
},
|
||||
{
|
||||
Label: "Alert API Url",
|
||||
@@ -79,12 +38,12 @@ func init() {
|
||||
},
|
||||
{
|
||||
Label: "Auto close incidents",
|
||||
Element: alerting.ElementTypeSwitch,
|
||||
Element: alerting.ElementTypeCheckbox,
|
||||
Description: "Automatically close alerts in OpsGenie once the alert goes back to ok.",
|
||||
PropertyName: "autoClose",
|
||||
}, {
|
||||
Label: "Override priority",
|
||||
Element: alerting.ElementTypeSwitch,
|
||||
Element: alerting.ElementTypeCheckbox,
|
||||
Description: "Allow the alert priority to be set using the og_priority tag",
|
||||
PropertyName: "overridePriority",
|
||||
},
|
||||
|
||||
@@ -20,53 +20,6 @@ func init() {
|
||||
Description: "Sends notifications to PagerDuty",
|
||||
Heading: "PagerDuty settings",
|
||||
Factory: NewPagerdutyNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">PagerDuty settings</h3>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-14">Integration Key</span>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.integrationKey">
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-22"
|
||||
ng-init="ctrl.model.secureSettings.integrationKey = ctrl.model.settings.integrationKey || null; ctrl.model.settings.integrationKey = null;"
|
||||
ng-model="ctrl.model.secureSettings.integrationKey"
|
||||
placeholder="Pagerduty Integration Key"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.integrationKey">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.integrationKey = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-14">Severity</span>
|
||||
<div class="gf-form-select-wrapper width-14">
|
||||
<select
|
||||
class="gf-form-input"
|
||||
ng-model="ctrl.model.settings.severity"
|
||||
ng-options="s for s in ['critical', 'error', 'warning', 'info']">
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<gf-form-switch
|
||||
class="gf-form"
|
||||
label="Auto resolve incidents"
|
||||
label-class="width-14"
|
||||
checked="ctrl.model.settings.autoResolve"
|
||||
tooltip="Resolve incidents in pagerduty once the alert goes back to ok.">
|
||||
</gf-form-switch>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<gf-form-switch
|
||||
class="gf-form"
|
||||
label="Include message in details"
|
||||
label-class="width-14"
|
||||
checked="ctrl.model.settings.messageInDetails"
|
||||
tooltip="Move the alert message from the PD summary into the custom details. This changes the custom details object and may break event rules you have configured">
|
||||
</gf-form-switch>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Integration Key",
|
||||
@@ -101,10 +54,16 @@ func init() {
|
||||
},
|
||||
{
|
||||
Label: "Auto resolve incidents",
|
||||
Element: alerting.ElementTypeSwitch,
|
||||
Element: alerting.ElementTypeCheckbox,
|
||||
Description: "Resolve incidents in pagerduty once the alert goes back to ok.",
|
||||
PropertyName: "autoResolve",
|
||||
},
|
||||
{
|
||||
Label: "Include message in details",
|
||||
Element: alerting.ElementTypeCheckbox,
|
||||
Description: "Move the alert message from the PD summary into the custom details. This changes the custom details object and may break event rules you have configured",
|
||||
PropertyName: "messageInDetails",
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
@@ -17,31 +17,6 @@ import (
|
||||
const pushoverEndpoint = "https://api.pushover.net/1/messages.json"
|
||||
|
||||
func init() {
|
||||
sounds := `
|
||||
'default',
|
||||
'pushover',
|
||||
'bike',
|
||||
'bugle',
|
||||
'cashregister',
|
||||
'classical',
|
||||
'cosmic',
|
||||
'falling',
|
||||
'gamelan',
|
||||
'incoming',
|
||||
'intermission',
|
||||
'magic',
|
||||
'mechanical',
|
||||
'pianobar',
|
||||
'siren',
|
||||
'spacealarm',
|
||||
'tugboat',
|
||||
'alien',
|
||||
'climb',
|
||||
'persistent',
|
||||
'echo',
|
||||
'updown',
|
||||
'none'`
|
||||
|
||||
soundOptions := []alerting.SelectOption{
|
||||
{
|
||||
Value: "default",
|
||||
@@ -122,76 +97,6 @@ func init() {
|
||||
Description: "Sends HTTP POST request to the Pushover API",
|
||||
Heading: "Pushover settings",
|
||||
Factory: NewPushoverNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Pushover settings</h3>
|
||||
<div class="gf-form">
|
||||
<label class="gf-form-label width-10">API Token</label>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.apiToken">
|
||||
<input type="text"
|
||||
required
|
||||
class="gf-form-input"
|
||||
ng-init="ctrl.model.secureSettings.apiToken = ctrl.model.settings.apiToken || null; ctrl.model.settings.apiToken = null;"
|
||||
ng-model="ctrl.model.secureSettings.apiToken"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.apiToken">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.apiToken = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<label class="gf-form-label max-width-10">User Key(s)</label>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.userKey">
|
||||
<input type="text"
|
||||
required
|
||||
class="gf-form-input"
|
||||
ng-init="ctrl.model.secureSettings.userKey = ctrl.model.settings.userKey || null; ctrl.model.settings.userKey = null;"
|
||||
ng-model="ctrl.model.secureSettings.userKey"
|
||||
placeholder="comma-separated list"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.userKey">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.userKey = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">Device(s) (optional)</span>
|
||||
<input type="text" class="gf-form-input" placeholder="comma-separated list; leave empty to send to all devices" ng-model="ctrl.model.settings.device"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">Priority</span>
|
||||
<select class="gf-form-input max-width-14" ng-model="ctrl.model.settings.priority" ng-options="v as k for (k, v) in {
|
||||
Emergency: '2',
|
||||
High: '1',
|
||||
Normal: '0',
|
||||
Low: '-1',
|
||||
Lowest: '-2'
|
||||
}" ng-init="ctrl.model.settings.priority=ctrl.model.settings.priority||'0'"></select>
|
||||
</div>
|
||||
<div class="gf-form" ng-show="ctrl.model.settings.priority == '2'">
|
||||
<span class="gf-form-label width-10">Retry</span>
|
||||
<input type="text" class="gf-form-input max-width-14" ng-required="ctrl.model.settings.priority == '2'" placeholder="minimum 30 seconds" ng-model="ctrl.model.settings.retry" ng-init="ctrl.model.settings.retry=ctrl.model.settings.retry||'60'></input>
|
||||
</div>
|
||||
<div class="gf-form" ng-show="ctrl.model.settings.priority == '2'">
|
||||
<span class="gf-form-label width-10">Expire</span>
|
||||
<input type="text" class="gf-form-input max-width-14" ng-required="ctrl.model.settings.priority == '2'" placeholder="maximum 86400 seconds" ng-model="ctrl.model.settings.expire" ng-init="ctrl.model.settings.expire=ctrl.model.settings.expire||'3600'"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">Alerting sound</span>
|
||||
<select class="gf-form-input max-width-14" ng-model="ctrl.model.settings.sound" ng-options="s for s in [
|
||||
` + sounds + `
|
||||
]" ng-init="ctrl.model.settings.sound=ctrl.model.settings.sound||'default'"></select>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">OK sound</span>
|
||||
<select class="gf-form-input max-width-14" ng-model="ctrl.model.settings.okSound" ng-options="s for s in [
|
||||
` + sounds + `
|
||||
]" ng-init="ctrl.model.settings.okSound=ctrl.model.settings.okSound||'default'"></select>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "API Token",
|
||||
@@ -200,6 +105,7 @@ func init() {
|
||||
Placeholder: "Application token",
|
||||
PropertyName: "apiToken",
|
||||
Required: true,
|
||||
Secure: true,
|
||||
},
|
||||
{
|
||||
Label: "User key(s)",
|
||||
@@ -208,6 +114,7 @@ func init() {
|
||||
Placeholder: "comma-separated list",
|
||||
PropertyName: "userKey",
|
||||
Required: true,
|
||||
Secure: true,
|
||||
},
|
||||
{
|
||||
Label: "Device(s) (optional)",
|
||||
|
||||
@@ -18,41 +18,6 @@ func init() {
|
||||
Description: "Sends HTTP POST request to a Sensu API",
|
||||
Heading: "Sensu settings",
|
||||
Factory: NewSensuNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Sensu settings</h3>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">Url</span>
|
||||
<input type="text" required class="gf-form-input max-width-26" ng-model="ctrl.model.settings.url" placeholder="http://sensu-api.local:4567/results"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">Source</span>
|
||||
<input type="text" class="gf-form-input max-width-14" ng-model="ctrl.model.settings.source" bs-tooltip="'If empty rule id will be used'" data-placement="right"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">Handler</span>
|
||||
<input type="text" class="gf-form-input max-width-14" ng-model="ctrl.model.settings.handler" placeholder="default"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">Username</span>
|
||||
<input type="text" class="gf-form-input max-width-14" ng-model="ctrl.model.settings.username"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<label class="gf-form-label width-10">Password</label>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.password">
|
||||
<input type="text"
|
||||
required
|
||||
class="gf-form-input max-width-14"
|
||||
ng-init="ctrl.model.secureSettings.password = ctrl.model.settings.password || null; ctrl.model.settings.password = null;"
|
||||
ng-model="ctrl.model.secureSettings.password"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.password">
|
||||
<input type="text" class="gf-form-input max-width-14" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.password = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Url",
|
||||
@@ -87,6 +52,7 @@ func init() {
|
||||
Element: alerting.ElementTypeInput,
|
||||
InputType: alerting.InputTypePassword,
|
||||
PropertyName: "passsword ",
|
||||
Secure: true,
|
||||
},
|
||||
},
|
||||
})
|
||||
|
||||
@@ -27,123 +27,6 @@ func init() {
|
||||
Description: "Sends notifications to Slack via Slack Webhooks",
|
||||
Heading: "Slack settings",
|
||||
Factory: NewSlackNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Slack settings</h3>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Url</span>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.url">
|
||||
<input type="text"
|
||||
required
|
||||
class="gf-form-input max-width-30"
|
||||
ng-init="ctrl.model.secureSettings.url = ctrl.model.settings.url || null; ctrl.model.settings.url = null;"
|
||||
ng-model="ctrl.model.secureSettings.url"
|
||||
placeholder="Slack incoming webhook url">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.url">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.url = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Recipient</span>
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.recipient"
|
||||
data-placement="right">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
Override default channel or user, use #channel-name, @username (has to be all lowercase, no whitespace), or user/channel Slack ID
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Username</span>
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.username"
|
||||
data-placement="right">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
Set the username for the bot's message
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Icon emoji</span>
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.icon_emoji"
|
||||
data-placement="right">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
Provide an emoji to use as the icon for the bot's message. Overrides the icon URL
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Icon URL</span>
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.icon_url"
|
||||
data-placement="right">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
Provide a URL to an image to use as the icon for the bot's message
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Mention Users</span>
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.mentionUsers"
|
||||
data-placement="right">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
Mention one or more users (comma separated) when notifying in a channel, by ID (you can copy this from the user's Slack profile)
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Mention Groups</span>
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.mentionGroups"
|
||||
data-placement="right">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
Mention one or more groups (comma separated) when notifying in a channel (you can copy this from the group's Slack profile URL)
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Mention Channel</span>
|
||||
<select
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.mentionChannel"
|
||||
data-placement="right">
|
||||
<option value="">Disabled</option>
|
||||
<option value="here">Every active channel member</option>
|
||||
<option value="channel">Every channel member</option>
|
||||
</select>
|
||||
<info-popover mode="right-absolute">
|
||||
Mention whole channel or just active members when notifying
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<div class="gf-form gf-form--v-stretch"><label class="gf-form-label width-8">Token</label></div>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.token">
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-init="ctrl.model.secureSettings.token = ctrl.model.settings.token || null; ctrl.model.settings.token = null;"
|
||||
ng-model="ctrl.model.secureSettings.token"
|
||||
data-placement="right">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
Provide a bot token to use the Slack file.upload API (starts with "xoxb"). Specify Recipient for this to work
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.token">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.token = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Url",
|
||||
@@ -152,6 +35,7 @@ func init() {
|
||||
Placeholder: "Slack incoming webhook url",
|
||||
PropertyName: "url",
|
||||
Required: true,
|
||||
Secure: true,
|
||||
},
|
||||
{
|
||||
Label: "Recipient",
|
||||
@@ -172,14 +56,14 @@ func init() {
|
||||
Element: alerting.ElementTypeInput,
|
||||
InputType: alerting.InputTypeText,
|
||||
Description: "Provide an emoji to use as the icon for the bot's message. Overrides the icon URL.",
|
||||
PropertyName: "icon_emoji",
|
||||
PropertyName: "iconEmoji",
|
||||
},
|
||||
{
|
||||
Label: "Icon URL",
|
||||
Element: alerting.ElementTypeInput,
|
||||
InputType: alerting.InputTypeText,
|
||||
Description: "Provide a URL to an image to use as the icon for the bot's message",
|
||||
PropertyName: "icon_url",
|
||||
PropertyName: "iconUrl",
|
||||
},
|
||||
{
|
||||
Label: "Mention Users",
|
||||
@@ -221,6 +105,7 @@ func init() {
|
||||
InputType: alerting.InputTypeText,
|
||||
Description: "Provide a bot token to use the Slack file.upload API (starts with \"xoxb\"). Specify Recipient for this to work",
|
||||
PropertyName: "token",
|
||||
Secure: true,
|
||||
},
|
||||
},
|
||||
})
|
||||
|
||||
@@ -16,13 +16,6 @@ func init() {
|
||||
Description: "Sends notifications using Incoming Webhook connector to Microsoft Teams",
|
||||
Heading: "Teams settings",
|
||||
Factory: NewTeamsNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Teams settings</h3>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-6">Url</span>
|
||||
<input type="text" InputType class="gf-form-input max-width-30" ng-model="ctrl.model.settings.url" placeholder="Teams incoming webhook url"></input>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "URL",
|
||||
@@ -30,6 +23,7 @@ func init() {
|
||||
InputType: alerting.InputTypeText,
|
||||
Placeholder: "Teams incoming webhook url",
|
||||
PropertyName: "url",
|
||||
Required: true,
|
||||
},
|
||||
},
|
||||
})
|
||||
|
||||
@@ -28,37 +28,6 @@ func init() {
|
||||
Description: "Sends notifications to Telegram",
|
||||
Heading: "Telegram API settings",
|
||||
Factory: NewTelegramNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Telegram API settings</h3>
|
||||
<div class="gf-form max-width-30">
|
||||
<label class="gf-form-label width-10">BOT API Token</label>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.bottoken">
|
||||
<input type="text"
|
||||
required
|
||||
class="gf-form-input max-width-30"
|
||||
ng-init="ctrl.model.secureSettings.bottoken = ctrl.model.settings.bottoken || null; ctrl.model.settings.bottoken = null;"
|
||||
ng-model="ctrl.model.secureSettings.bottoken"
|
||||
placeholder="Telegram BOT API Token"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.bottoken">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.bottoken = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<label class="gf-form-label width-10">Chat ID</label>
|
||||
<input type="text"
|
||||
required
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.chatid"
|
||||
placeholder="Telegram Chat ID"
|
||||
data-placement="right">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">Integer Telegram Chat Identifier</info-popover>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "BOT API Token",
|
||||
@@ -67,6 +36,7 @@ func init() {
|
||||
Placeholder: "Telegram BOT API Token",
|
||||
PropertyName: "bottoken",
|
||||
Required: true,
|
||||
Secure: true,
|
||||
},
|
||||
{
|
||||
Label: "Chat ID",
|
||||
|
||||
@@ -24,55 +24,6 @@ func init() {
|
||||
Info: "Notifications can be configured for any Threema Gateway ID of type \"Basic\". End-to-End IDs are not currently supported." +
|
||||
"The Threema Gateway ID can be set up at https://gateway.threema.ch/.",
|
||||
Factory: NewThreemaNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Threema Gateway settings</h3>
|
||||
<p>
|
||||
Notifications can be configured for any Threema Gateway ID of type
|
||||
"Basic". End-to-End IDs are not currently supported.
|
||||
</p>
|
||||
<p>
|
||||
The Threema Gateway ID can be set up at
|
||||
<a href="https://gateway.threema.ch/" target="_blank" rel="noopener noreferrer">https://gateway.threema.ch/</a>.
|
||||
</p>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Gateway ID</span>
|
||||
<input type="text" required maxlength="8" pattern="\*[0-9A-Z]{7}"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.gateway_id"
|
||||
placeholder="*3MAGWID">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
Your 8 character Threema Gateway ID (starting with a *)
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Recipient ID</span>
|
||||
<input type="text" required maxlength="8" pattern="[0-9A-Z]{8}"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-model="ctrl.model.settings.recipient_id"
|
||||
placeholder="YOUR3MID">
|
||||
</input>
|
||||
<info-popover mode="right-absolute">
|
||||
The 8 character Threema ID that should receive the alerts
|
||||
</info-popover>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<label class="gf-form-label width-8">API Secret</label>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.api_secret">
|
||||
<input type="text"
|
||||
required
|
||||
class="gf-form-input max-width-30"
|
||||
ng-init="ctrl.model.secureSettings.api_secret = ctrl.model.settings.api_secret || null; ctrl.model.settings.api_secret = null;"
|
||||
ng-model="ctrl.model.secureSettings.api_secret"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.api_secret">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.api_secret = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Gateway ID",
|
||||
@@ -101,6 +52,7 @@ func init() {
|
||||
Description: "Your Threema Gateway API secret.",
|
||||
PropertyName: "api_secret",
|
||||
Required: true,
|
||||
Secure: true,
|
||||
},
|
||||
},
|
||||
})
|
||||
|
||||
@@ -25,29 +25,6 @@ func init() {
|
||||
Description: "Sends notifications to VictorOps",
|
||||
Heading: "VictorOps settings",
|
||||
Factory: NewVictoropsNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">VictorOps settings</h3>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-6">Url</span>
|
||||
<input type="text" required class="gf-form-input max-width-30" ng-model="ctrl.model.settings.url" placeholder="VictorOps url"></input>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<span class="gf-form-label width-10">No Data Alert Type</span>
|
||||
<div class="gf-form-select-wrapper width-14">
|
||||
<select class="gf-form-input" ng-model="ctrl.model.settings.noDataAlertType" ng-options="t for t in ['CRITICAL', 'WARNING']" ng-init="ctrl.model.settings.noDataAlertType=ctrl.model.settings.noDataAlertType || '` + AlertStateWarning + `'">
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div class="gf-form">
|
||||
<gf-form-switch
|
||||
class="gf-form"
|
||||
label="Auto resolve incidents"
|
||||
label-class="width-14"
|
||||
checked="ctrl.model.settings.autoResolve"
|
||||
tooltip="Resolve incidents in VictorOps once the alert goes back to ok.">
|
||||
</gf-form-switch>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Url",
|
||||
@@ -60,7 +37,7 @@ func init() {
|
||||
{
|
||||
Label: "Auto resolve incidents",
|
||||
Description: "Resolve incidents in VictorOps once the alert goes back to ok.",
|
||||
Element: alerting.ElementTypeSwitch,
|
||||
Element: alerting.ElementTypeCheckbox,
|
||||
PropertyName: "autoResolve",
|
||||
},
|
||||
},
|
||||
|
||||
@@ -15,39 +15,6 @@ func init() {
|
||||
Description: "Sends HTTP POST request to a URL",
|
||||
Heading: "Webhook settings",
|
||||
Factory: NewWebHookNotifier,
|
||||
OptionsTemplate: `
|
||||
<h3 class="page-heading">Webhook settings</h3>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Url</span>
|
||||
<input type="text" required class="gf-form-input max-width-26" ng-model="ctrl.model.settings.url"></input>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Http Method</span>
|
||||
<div class="gf-form-select-wrapper max-width-30">
|
||||
<select class="gf-form-input" ng-model="ctrl.model.settings.httpMethod" ng-options="t for t in ['POST', 'PUT']">
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<span class="gf-form-label width-8">Username</span>
|
||||
<input type="text" class="gf-form-input max-width-30" ng-model="ctrl.model.settings.username"></input>
|
||||
</div>
|
||||
<div class="gf-form max-width-30">
|
||||
<div class="gf-form gf-form--v-stretch"><label class="gf-form-label width-8">Password</label></div>
|
||||
<div class="gf-form gf-form--grow" ng-if="!ctrl.model.secureFields.password">
|
||||
<input type="text"
|
||||
class="gf-form-input max-width-30"
|
||||
ng-init="ctrl.model.secureSettings.password = ctrl.model.settings.password || null; ctrl.model.settings.password = null;"
|
||||
ng-model="ctrl.model.secureSettings.password"
|
||||
data-placement="right">
|
||||
</input>
|
||||
</div>
|
||||
<div class="gf-form" ng-if="ctrl.model.secureFields.password">
|
||||
<input type="text" class="gf-form-input max-width-18" disabled="disabled" value="configured" />
|
||||
<a class="btn btn-secondary gf-form-btn" href="#" ng-click="ctrl.model.secureFields.password = false">reset</a>
|
||||
</div>
|
||||
</div>
|
||||
`,
|
||||
Options: []alerting.NotifierOption{
|
||||
{
|
||||
Label: "Url",
|
||||
@@ -82,6 +49,7 @@ func init() {
|
||||
Element: alerting.ElementTypeInput,
|
||||
InputType: alerting.InputTypePassword,
|
||||
PropertyName: "password",
|
||||
Secure: true,
|
||||
},
|
||||
},
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user