Skip to content

Commit

Permalink
Merge pull request #26 from ohlol/master
Browse files Browse the repository at this point in the history
Sensu plugin
  • Loading branch information
collinvandyck committed Apr 24, 2013
2 parents e90125b + d9e2430 commit f74bdc3
Show file tree
Hide file tree
Showing 3 changed files with 223 additions and 3 deletions.
5 changes: 2 additions & 3 deletions .gitignore
@@ -1,6 +1,5 @@
.DS_Store
boundary.conf
*.swp
gesture.conf
bin/*
gesture
gesture
*.conf
2 changes: 2 additions & 0 deletions gesture.go
Expand Up @@ -10,6 +10,7 @@ import (
"gesture/plugin/identity"
"gesture/plugin/matcher"
"gesture/plugin/memegenerator"
"gesture/plugin/sensu"
"gesture/plugin/twitter"
"gesture/plugin/youtube"
"log"
Expand All @@ -23,6 +24,7 @@ func loadPlugins(bot *core.Gobot) {
identity.Create(bot)
memegenerator.Create(bot)
graphite.Create(bot)
sensu.Create(bot)
all.Create(bot)
}

Expand Down
219 changes: 219 additions & 0 deletions plugin/sensu/sensu.go
@@ -0,0 +1,219 @@
package sensu

import (
"bytes"
"encoding/json"
"fmt"
"gesture/core"
"gesture/util"
"log"
"net/http"
"strings"
"time"
)

type sensuEventData struct {
Client string
Check string
Occurrences uint64
Output string
Flapping bool
Status uint8
}

type sensuEvent interface {
statusAsString()
}

type eventsResponse []sensuEventData

type stashList []string

type postData struct {
timestamp int64
}

func Create(bot *core.Gobot) {
config, found := bot.Config.Plugins["sensu"]
if !found {
log.Printf("No sensu config found")
return
}

envs := make(map[string]string)
for e, u := range config["environments"].(map[string]interface{}) {
envs[e] = fmt.Sprintf("%s", u)
}

bot.ListenFor("^sensu (.*)", func(msg core.Message, matches []string) error {
cmdArgs := strings.Split(matches[1], " ")
switch cmdArgs[0] {
case "events":
if len(cmdArgs) > 1 {
if err, events := getEvents(envs[cmdArgs[1]]); err != nil {
return err
} else {
if len(events) > 0 {
for _, event := range events {
msg.Send(fmt.Sprintf("%s: %s", cmdArgs[1], event.toString()))
time.Sleep(100 * time.Millisecond)
}
} else {
msg.Send(fmt.Sprintf("%s: No current open alerts.", cmdArgs[1]))
}
}
} else {
for env, url := range envs {
if err, events := getEvents(url); err != nil {
return err
} else {
if len(events) > 0 {
for _, event := range events {
msg.Send(fmt.Sprintf("%s: %s", env, event.toString()))
time.Sleep(100 * time.Millisecond)
}
} else {
msg.Send(fmt.Sprintf("%s: No current open alerts.", env))
}
}
}
}
case "silence":
var (
env string
target string
)

if len(cmdArgs) > 2 {
env = envs[cmdArgs[1]]
target = cmdArgs[2]
} else {
env = ""
target = cmdArgs[1]
}

if err := silence(env, target); err != nil {
return err
} else {
msg.Send(fmt.Sprintf("silenced %s in env: %s", cmdArgs[2], cmdArgs[1]))
}
case "silenced":
if len(cmdArgs) > 1 {
if err, silenced := getSilenced(envs[cmdArgs[1]]); err != nil {
return err
} else {
if len(silenced) > 0 {
for _, s := range silenced {
msg.Send(fmt.Sprintf("%s: %s", cmdArgs[1], s))
time.Sleep(100 * time.Millisecond)
}
} else {
msg.Send(fmt.Sprintf("%s: Nothing currently silenced.", cmdArgs[1]))
}
}
} else {
for env, url := range envs {
if err, silenced := getSilenced(url); err != nil {
return err
} else {
if len(silenced) > 0 {
for _, s := range silenced {
msg.Send(fmt.Sprintf("%s: %s", env, s))
time.Sleep(100 * time.Millisecond)
}
} else {
msg.Send(fmt.Sprintf("%s: Nothing currently silenced.", env))
}
}
}
}
case "unsilence":
var (
env string
target string
)

if len(cmdArgs) > 2 {
env = envs[cmdArgs[1]]
target = cmdArgs[2]
} else {
env = ""
target = cmdArgs[1]
}

if err := unsilence(env, target); err != nil {
fmt.Println(err)
} else {
msg.Send(fmt.Sprintf("silenced %s in env: %s", cmdArgs[2], cmdArgs[1]))
}
}

return nil
})
}

func getEvents(sensuUrl string) (error, eventsResponse) {
eventsUrl := fmt.Sprintf("%s/events", sensuUrl)
var eventsResponse eventsResponse
err := util.UnmarshalUrl(eventsUrl, &eventsResponse)
return err, eventsResponse
}

func getStashes(sensuUrl string) (error, stashList) {
stashesUrl := fmt.Sprintf("%s/stashes", sensuUrl)
var stashResponse stashList
err := util.UnmarshalUrl(stashesUrl, &stashResponse)
return err, stashResponse
}

func getSilenced(sensuUrl string) (error, []string) {
var silenced []string
if err, stashes := getStashes(sensuUrl); err != nil {
return err, silenced
} else {
for _, stash := range stashes {
if strings.HasPrefix(stash, "silence/") {
silenced = append(silenced, string(stash[8:]))
}
}
}
return nil, silenced
}

func silence(sensuUrl string, target string) error {
data := postData{timestamp: time.Now().Unix()}
marshalled, err := json.Marshal(data)
if err != nil {
return err
}

silenceUrl := fmt.Sprintf("%s/stash/silence/%s", sensuUrl, target)
_, err = http.Post(silenceUrl, "application/json", bytes.NewBuffer(marshalled))
return err
}

func unsilence(sensuUrl string, target string) error {
silenceUrl := fmt.Sprintf("%s/stash/silence/%s", sensuUrl, target)
req, _ := http.NewRequest("DELETE", silenceUrl, nil)
_, err := http.DefaultClient.Do(req)
return err
}

func (event *sensuEventData) statusAsString() string {
var status string
switch event.Status {
case 0:
status = "OK"
case 1:
status = "WARNING"
case 2:
status = "CRITICAL"
case 3:
status = "UNKNOWN"
}
return status
}

func (event *sensuEventData) toString() string {
return fmt.Sprintf("%s: %s/%s - %s", event.statusAsString(), event.Client, event.Check, event.Output)
}

0 comments on commit f74bdc3

Please sign in to comment.