Skip to content

Commit

Permalink
Add slack provider for events
Browse files Browse the repository at this point in the history
  • Loading branch information
XCiber committed Jan 17, 2022
1 parent 480f659 commit dff91de
Show file tree
Hide file tree
Showing 5 changed files with 183 additions and 1 deletion.
8 changes: 7 additions & 1 deletion examples/events.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,4 +27,10 @@ sre/provider/grafana.go:127 Annotation 1502808. Annotation added

## DataDog UO
![DataDog](/examples/datadog-events.png)
![DataDog](/examples/datadog-events2.png)
![DataDog](/examples/datadog-events2.png)

## Slack UI

Send simple messages from `name` field or structured slack BlockKit json from `attributes["payload"]`(if present)

![Slack](/examples/slack-events.png)
57 changes: 57 additions & 0 deletions examples/events_slack.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
package main

import (
_ "embed"
"time"

"github.com/devopsext/sre/common"
"github.com/devopsext/sre/provider"
)

//go:embed slack.json
var payload []byte

var logs = common.NewLogs()
var events = common.NewEvents()

func test() {

events.Now(":exclamation: First", nil)

m := make(map[string]string)
m["payload"] = string(payload)

events.Now(":grey_exclamation:Second", m)
events.Now(":grey_question: *Third*", nil)
}

func main() {

defer logs.Stop() // finalize logs delivery
defer events.Stop() // finalize events delivery

// initialize Stdout logger
stdout := provider.NewStdout(provider.StdoutOptions{
Format: "template",
Level: "debug",
Template: "{{.file}} {{.msg}}",
TimestampFormat: time.RFC3339Nano,
TextColors: true,
})
// set caller offset for file:line proper usage
stdout.SetCallerOffset(2)

// add Stdout logger
logs.Register(stdout)

slack := provider.NewSlackEventer(provider.SlackOptions{
WebHook: "",
Tags: "",
Timeout: 2,
}, logs, stdout)

// add events
events.Register(slack)

test()
}
Binary file added examples/slack-events.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
35 changes: 35 additions & 0 deletions examples/slack.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
{
"blocks": [
{
"type": "header",
"text": {
"type": "plain_text",
"text": "Daily News",
"emoji": true
}
},
{
"type": "divider"
},
{
"type": "section",
"text": {
"type": "mrkdwn",
"text": "`06:45 UTC (08:45 ETT)`:\t:grey_exclamation:\t| Germany_Industrial Orders MM"
}
},
{
"type": "section",
"fields": [
{
"type": "mrkdwn",
"text": "*Symbol*: EUR / EUR,CHF,XAG,XAU"
},
{
"type": "mrkdwn",
"text": "*Type*: Industry Sector"
}
]
}
]
}
84 changes: 84 additions & 0 deletions provider/slack.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
package provider

import (
"bytes"
"context"
"fmt"
"github.com/devopsext/sre/common"
"github.com/devopsext/utils"
"io/ioutil"
"net/http"
"time"
)

type SlackOptions struct {
WebHook string
Tags string
Timeout int
}

type SlackEventer struct {
options SlackOptions
logger common.Logger
tags []string
client *http.Client
ctx context.Context
}

func (se *SlackEventer) Now(name string, attributes map[string]string) {
se.At(name, attributes, time.Now())
}

func (se *SlackEventer) At(name string, attributes map[string]string, when time.Time) {
se.Interval(name, attributes, when, when)
}

func (se *SlackEventer) Interval(name string, attributes map[string]string, begin, end time.Time) {
var body string

body = fmt.Sprintf("{\"text\": \"%s\"}", name)
if payload, ok := attributes["payload"]; ok {
body = payload
}

resp, err := http.Post(se.options.WebHook, "application/json", bytes.NewBuffer([]byte(body)))
if err != nil {
se.logger.Error("slack post:", err)
return
}

defer resp.Body.Close()

rBody, err := ioutil.ReadAll(resp.Body)
if err != nil {
se.logger.Error("slack post response:", err)
return
}
se.logger.Debug(string(rBody))
}

func (se *SlackEventer) Stop() {
se.client.CloseIdleConnections()
se.logger.Info("Slack Eventer stopped.")
}

func NewSlackEventer(options SlackOptions, logger common.Logger, stdout *Stdout) *SlackEventer {
if logger == nil {
logger = stdout
}

if utils.IsEmpty(options.WebHook) {
logger.Debug("Slack Eventer is disabled")
return nil
}

logger.Info("Slack Eventer is up…")

return &SlackEventer{
options: options,
logger: logger,
tags: common.MapToArray(common.GetKeyValues(options.Tags)),
client: common.MakeHttpClient(options.Timeout),
ctx: context.Background(),
}
}

0 comments on commit dff91de

Please sign in to comment.