Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add AWS SNS receiver #2615

Merged
merged 35 commits into from Jul 26, 2021
Merged
Show file tree
Hide file tree
Changes from 31 commits
Commits
Show all changes
35 commits
Select commit Hold shift + click to select a range
19e74f9
WIP - SNS receiver
Jun 10, 2021
5dcf4f5
ARN Auth start
Jun 11, 2021
74d1527
Add support for role arn, truncation, dedupe key and env auth
Jun 11, 2021
009f8b1
Use 1024 rather than 1000 for KB size, fix target arn, handle large S…
Jun 14, 2021
72d63a5
Remove isFifo config option; use template strings; use retier; other …
Jun 14, 2021
6519c39
Add some tests for sns receiver
Jun 15, 2021
af8406a
Check error type before unpacking awserr.requestFailure
Jun 15, 2021
68fa1bf
Add string length check to fifo check
Jun 15, 2021
b509a5b
Add subject template for subject field. Better check for supplied cre…
Jun 15, 2021
8d3b1b5
Add config docs
Jun 15, 2021
889fa96
Remove isFifoTopic test
Jun 15, 2021
c48b54b
Fix gosmpl linter issues
Jun 16, 2021
3a63cc2
Updated assets
pracucci Jun 16, 2021
6ada9a6
Cache fifo bool in the notifier
Jun 16, 2021
756cdda
Fix for golangci-lint warning
Jun 16, 2021
9d37d6c
More gofmt fixes
Jun 16, 2021
3446b35
Code review fixes: copy attributes, truncate all the messages, fix lo…
Jun 16, 2021
a56305a
Fix spacing from removing default api version
Jun 16, 2021
d4ff90b
Add missing template for aws region
Jun 16, 2021
b9b53f1
Code review fixes
Jun 17, 2021
63f9082
Fix docs spacing
Jun 17, 2021
4ebcaf9
Merge remote-tracking branch 'upstream/master' into sns-reciever
Jun 17, 2021
8911051
Make API URL optional, clear up credential logic
Jun 21, 2021
dfb4d1f
Fix linter error
Jun 21, 2021
9ff4ac3
Create new session if needed to get STS Creds
Jun 21, 2021
30a83f7
Use supplied user creds when creating an STS client
Jun 22, 2021
bd82f70
Fix spacing for client config
Jun 22, 2021
25e6d4e
Add common/sigv4 with the sigv4 config
Jun 23, 2021
208bed6
Update config docs to clarify fifo SNS deduplication strategy. Remove…
Jun 28, 2021
1322abd
Remove unused checkTopicFifoAttribute function
Jun 28, 2021
077b20d
Add error check when creating sns session
Jul 1, 2021
7ecb6bc
Check Error in unit test and clean up docs
Jul 6, 2021
4c2a5f1
Add sigv4 as a global config option
Jul 7, 2021
51b9368
Revert "Add sigv4 as a global config option"
Jul 9, 2021
a1260af
Break notify into submethods to create the session then create the pu…
Jul 9, 2021
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
4 changes: 2 additions & 2 deletions asset/assets_vfsdata.go

Large diffs are not rendered by default.

4 changes: 4 additions & 0 deletions cmd/alertmanager/main.go
Expand Up @@ -31,6 +31,7 @@ import (
"github.com/go-kit/kit/log"
"github.com/go-kit/kit/log/level"
"github.com/pkg/errors"
"github.com/prometheus/alertmanager/notify/sns"
"github.com/prometheus/client_golang/prometheus"
"github.com/prometheus/client_golang/prometheus/promhttp"
"github.com/prometheus/common/model"
Expand Down Expand Up @@ -165,6 +166,9 @@ func buildReceiverIntegrations(nc *config.Receiver, tmpl *template.Template, log
for i, c := range nc.PushoverConfigs {
add("pushover", i, c, func(l log.Logger) (notify.Notifier, error) { return pushover.New(c, tmpl, l) })
}
for i, c := range nc.SNSConfigs {
add("sns", i, c, func(l log.Logger) (notify.Notifier, error) { return sns.New(c, tmpl, l) })
}
if errs.Len() > 0 {
return nil, &errs
}
Expand Down
9 changes: 9 additions & 0 deletions config/config.go
Expand Up @@ -242,6 +242,9 @@ func resolveFilepaths(baseDir string, cfg *Config) {
for _, cfg := range receiver.WechatConfigs {
cfg.HTTPConfig.SetDirectory(baseDir)
}
for _, cfg := range receiver.SNSConfigs {
cfg.HTTPConfig.SetDirectory(baseDir)
}
}
}

Expand Down Expand Up @@ -447,6 +450,11 @@ func (c *Config) UnmarshalYAML(unmarshal func(interface{}) error) error {
voc.APIKey = c.Global.VictorOpsAPIKey
}
}
for _, sns := range rcv.SNSConfigs {
if sns.HTTPConfig == nil {
sns.HTTPConfig = c.Global.HTTPConfig
}
}
names[rcv.Name] = struct{}{}
}

Expand Down Expand Up @@ -784,6 +792,7 @@ type Receiver struct {
WechatConfigs []*WechatConfig `yaml:"wechat_configs,omitempty" json:"wechat_configs,omitempty"`
PushoverConfigs []*PushoverConfig `yaml:"pushover_configs,omitempty" json:"pushover_configs,omitempty"`
VictorOpsConfigs []*VictorOpsConfig `yaml:"victorops_configs,omitempty" json:"victorops_configs,omitempty"`
SNSConfigs []*SNSConfig `yaml:"sns_configs,omitempty" json:"sns_configs,omitempty"`
}

// UnmarshalYAML implements the yaml.Unmarshaler interface for Receiver.
Expand Down
16 changes: 15 additions & 1 deletion config/config_test.go
Expand Up @@ -26,7 +26,7 @@ import (
commoncfg "github.com/prometheus/common/config"
"github.com/prometheus/common/model"
"github.com/stretchr/testify/require"
yaml "gopkg.in/yaml.v2"
"gopkg.in/yaml.v2"
)

func TestLoadEmptyString(t *testing.T) {
Expand Down Expand Up @@ -1020,6 +1020,20 @@ func TestSlackGlobalAPIURLFile(t *testing.T) {
}
}

func TestValidSNSConfig(t *testing.T) {
_, err := LoadFile("testdata/conf.sns-topic-arn.yml")
if err != nil {
t.Fatalf("Error parsing %s: %s", "testdata/conf.sns-topic-arn.yml\"", err)
}
}

func TestInvalidSNSConfig(t *testing.T) {
_, err := LoadFile("testdata/conf.sns-invalid.yml")
if err == nil {
treid314 marked this conversation as resolved.
Show resolved Hide resolved
t.Fatalf("expected error with missing fields on SNS config")
}
}

func TestUnmarshalHostPort(t *testing.T) {
for _, tc := range []struct {
in string
Expand Down
41 changes: 41 additions & 0 deletions config/notifiers.go
Expand Up @@ -20,6 +20,7 @@ import (
"time"

"github.com/pkg/errors"
"github.com/prometheus/common/sigv4"

commoncfg "github.com/prometheus/common/config"
)
Expand Down Expand Up @@ -127,6 +128,15 @@ var (
Expire: duration(1 * time.Hour),
HTML: false,
}

// DefaultSNSConfig defines default values for SNS configurations.
DefaultSNSConfig = SNSConfig{
NotifierConfig: NotifierConfig{
VSendResolved: true,
},
Subject: `{{ template "sns.default.subject" . }}`,
Message: `{{ template "sns.default.message" . }}`,
}
)

// NotifierConfig contains base options common across all notifier configurations.
Expand Down Expand Up @@ -579,3 +589,34 @@ func (c *PushoverConfig) UnmarshalYAML(unmarshal func(interface{}) error) error
}
return nil
}

type SNSConfig struct {
NotifierConfig `yaml:",inline" json:",inline"`

HTTPConfig *commoncfg.HTTPClientConfig `yaml:"http_config,omitempty" json:"http_config,omitempty"`

APIUrl string `yaml:"api_url,omitempty" json:"api_url,omitempty"`
Sigv4 sigv4.SigV4Config `yaml:"sigv4" json:"sigv4"`
TopicARN string `yaml:"topic_arn,omitempty" json:"topic_arn,omitempty"`
PhoneNumber string `yaml:"phone_number,omitempty" json:"phone_number,omitempty"`
TargetARN string `yaml:"target_arn,omitempty" json:"target_arn,omitempty"`
Subject string `yaml:"subject,omitempty" json:"subject,omitempty"`
Message string `yaml:"message,omitempty" json:"message,omitempty"`
Attributes map[string]string `yaml:"attributes,omitempty" json:"attributes,omitempty"`
}

// UnmarshalYAML implements the yaml.Unmarshaler interface.
func (c *SNSConfig) UnmarshalYAML(unmarshal func(interface{}) error) error {
*c = DefaultSNSConfig
type plain SNSConfig
if err := unmarshal((*plain)(c)); err != nil {
return err
}
if (c.TargetARN == "") != (c.TopicARN == "") != (c.PhoneNumber == "") {
return fmt.Errorf("must provide either a Target ARN, Topic ARN, or Phone Number for SNS config")
}
if (c.Sigv4.AccessKey == "") != (c.Sigv4.SecretKey == "") {
return fmt.Errorf("must provide a AWS SigV4 Access key and Secret Key if credentials are specified in the SNS config")
}
return nil
}
14 changes: 14 additions & 0 deletions config/testdata/conf.sns-invalid.yml
@@ -0,0 +1,14 @@
route:
receiver: 'sns-api-notifications'
group_by: [alertname]

receivers:
- name: 'sns-api-notifications'
sns_configs:
- api_url: https://sns.us-east-2.amazonaws.com
sigv4:
region: us-east-2
access_key: access_key
secret_key: secret_ket
attributes:
severity: Sev2
15 changes: 15 additions & 0 deletions config/testdata/conf.sns-topic-arn.yml
@@ -0,0 +1,15 @@
route:
receiver: 'sns-api-notifications'
group_by: [alertname]

receivers:
- name: 'sns-api-notifications'
sns_configs:
- api_url: https://sns.us-east-2.amazonaws.com
topic_arn: arn:aws:sns:us-east-2:123456789012:My-Topic
sigv4:
region: us-east-2
access_key: access_key
secret_key: secret_ket
attributes:
severity: Sev2
58 changes: 58 additions & 0 deletions docs/configuration.md
Expand Up @@ -693,6 +693,64 @@ value: <tmpl_string>
[ short: <boolean> | default = slack_config.short_fields ]
```

## `<sns_configs>`
```yaml
# Whether or not to notify about resolved alerts.
[ send_resolved: <boolean> | default = false ]

# The SNS API URL i.e. https://sns.us-east-2.amazonaws.com.
# If not specified, the SNS API URL from the SNS SDK will be used.
[api_url: <tmpl_string>]
treid314 marked this conversation as resolved.
Show resolved Hide resolved

# Configures AWS's Signature Verification 4 signing process to sign requests.
sigv4:
[ <sigv4_config> ]

# SNS topic ARN, i.e. arn:aws:sns:us-east-2:698519295917:My-Topic
# If you don't specify this value, you must specify a value for the phone_number or target_arn.
# If you are using a FIFO SNS topic you should set a message group interval longer than 5 minutes
# to prevent messages with the same group key being deduplicated by the SNS default deduplication window
[ topic_arn: <tmpl_string>]
treid314 marked this conversation as resolved.
Show resolved Hide resolved

# Subject line when the message is delivered to email endpoints.
[ subject: <tmpl_string> | default = '{{ template "sns.default.subject" .}}' ]

# Phone number if message is delivered via SMS in E.164 format.
# If you don't specify this value, you must specify a value for the topic_arn or target_arn.
[ phone_number: <tmpl_string> ]

# The mobile platform endpoint ARN if message is delivered via mobile notifications.
# If you don't specify this value, you must specify a value for the topic_arn or phone_number.
[ target_arn: <tmpl_string> ]

# The message content of the SNS notification.
[ message: <tmpl_string> | default = '{{ template "sns.default.message" .}}' ]

# SNS message attributes.
attributes:
[key : value]
treid314 marked this conversation as resolved.
Show resolved Hide resolved

# The HTTP client's configuration.
[ http_config: <http_config> | default = global.http_config ]
treid314 marked this conversation as resolved.
Show resolved Hide resolved
```

###`<sigv4_config>`
treid314 marked this conversation as resolved.
Show resolved Hide resolved
```yaml
# The AWS region. If blank, the region from the default credentials chain is used.
[ region: <string> ]

# The AWS API keys. Both access_key and secret_key must be supplied or both must be blank.
# If blank the environment variables `AWS_ACCESS_KEY_ID` and `AWS_SECRET_ACCESS_KEY` are used.
[ access_key: <string> ]
[ secret_key: <secret> ]

# Named AWS profile used to authenticate.
[ profile: <string> ]

# AWS Role ARN, an alternative to using AWS API keys.
[ role_arn: <string> ]
```

## `<matcher>`

A matcher is a string with a syntax inspired by PromQL and OpenMetrics. The syntax of a matcher consists of three tokens:
Expand Down
8 changes: 5 additions & 3 deletions go.mod
Expand Up @@ -2,6 +2,7 @@ module github.com/prometheus/alertmanager

require (
github.com/alecthomas/units v0.0.0-20210208195552-ff826a37aa15
github.com/aws/aws-sdk-go v1.38.35
github.com/cenkalti/backoff/v4 v4.1.0
github.com/cespare/xxhash v1.1.0
github.com/go-kit/kit v0.10.0
Expand All @@ -22,16 +23,17 @@ require (
github.com/oklog/run v1.1.0
github.com/oklog/ulid v1.3.1
github.com/pkg/errors v0.9.1
github.com/prometheus/client_golang v1.10.0
github.com/prometheus/common v0.24.0
github.com/prometheus/client_golang v1.11.0
github.com/prometheus/common v0.29.0
github.com/prometheus/common/sigv4 v0.1.0
github.com/prometheus/exporter-toolkit v0.5.1
github.com/rs/cors v1.7.0
github.com/shurcooL/httpfs v0.0.0-20190707220628-8d4bc4ba7749
github.com/shurcooL/vfsgen v0.0.0-20200824052919-0d455de96546
github.com/stretchr/testify v1.7.0
github.com/xlab/treeprint v1.1.0
go.uber.org/atomic v1.5.0
golang.org/x/net v0.0.0-20210421230115-4e50805a0758
golang.org/x/net v0.0.0-20210525063256-abc453219eb5
golang.org/x/tools v0.1.0
gopkg.in/alecthomas/kingpin.v2 v2.2.6
gopkg.in/yaml.v2 v2.4.0
Expand Down