From a6f38b396676bb6ed1da70bd52defacfa2011712 Mon Sep 17 00:00:00 2001 From: Kirill Zaitsev Date: Thu, 2 Oct 2014 18:04:32 +0400 Subject: [PATCH] Added gitter support --- plugin/notify/gitter.go | 78 +++++++++++++++++++++++++++++++++++ plugin/notify/notification.go | 38 +++++++++++++++++ plugin/notify/slack.go | 28 +++---------- 3 files changed, 122 insertions(+), 22 deletions(-) create mode 100644 plugin/notify/gitter.go diff --git a/plugin/notify/gitter.go b/plugin/notify/gitter.go new file mode 100644 index 00000000..db9433ea --- /dev/null +++ b/plugin/notify/gitter.go @@ -0,0 +1,78 @@ +package notify + +import ( + "encoding/json" + "fmt" + + "github.com/drone/drone/shared/model" +) + +const ( + gitterEndpoint = "https://api.gitter.im/v1/rooms/%s/chatMessages" + gitterStartedMessage = "*Building* %s, commit [%s](%s), author %s" + gitterSuccessMessage = "*Success* %s, commit [%s](%s), author %s" + gitterFailureMessage = "*Failed* %s, commit [%s](%s), author %s" +) + +type Gitter struct { + RoomID string `yaml:"room_id,omitempty"` + Token string `yaml:"token,omitempty"` + Started bool `yaml:"on_started,omitempty"` + Success bool `yaml:"on_success,omitempty"` + Failure bool `yaml:"on_failure,omitempty"` +} + +func (g *Gitter) Send(context *model.Request) error { + switch { + case context.Commit.Status == "Started" && g.Started: + return g.sendStarted(context) + case context.Commit.Status == "Success" && g.Success: + return g.sendSuccess(context) + case context.Commit.Status == "Failure" && g.Failure: + return g.sendFailure(context) + } + + return nil +} + +func (g *Gitter) getMessage(context *model.Request, message string) string { + url := getBuildUrl(context) + return fmt.Sprintf(message, context.Repo.Name, context.Commit.ShaShort(), url, context.Commit.Author) +} + +func (g *Gitter) sendStarted(context *model.Request) error { + return g.send(g.getMessage(context, gitterStartedMessage)) +} + +func (g *Gitter) sendSuccess(context *model.Request) error { + return g.send(g.getMessage(context, gitterSuccessMessage)) +} + +func (g *Gitter) sendFailure(context *model.Request) error { + return g.send(g.getMessage(context, gitterFailureMessage)) +} + +// helper function to send HTTP requests +func (g *Gitter) send(msg string) error { + // data will get posted in this format + data := struct { + Text string `json:"text"` + }{msg} + + // data json encoded + payload, err := json.Marshal(data) + if err != nil { + return err + } + + // send payload + url := fmt.Sprintf(gitterEndpoint, g.RoomID) + + // create headers + headers := make(map[string]string) + headers["Authorization"] = fmt.Sprintf("Bearer %s", g.Token) + + go sendJson(url, payload, headers) + + return nil +} diff --git a/plugin/notify/notification.go b/plugin/notify/notification.go index 3f263aca..dab57f43 100644 --- a/plugin/notify/notification.go +++ b/plugin/notify/notification.go @@ -1,7 +1,10 @@ package notify import ( + "bytes" + "fmt" "log" + "net/http" "github.com/drone/drone/plugin/notify/email" "github.com/drone/drone/plugin/notify/github" @@ -23,6 +26,7 @@ type Notification struct { Hipchat *Hipchat `yaml:"hipchat,omitempty"` Irc *irc.IRC `yaml:"irc,omitempty"` Slack *Slack `yaml:"slack,omitempty"` + Gitter *Gitter `yaml:"gitter,omitempty"` GitHub github.GitHub `yaml:"--"` } @@ -68,6 +72,14 @@ func (n *Notification) Send(context *model.Request) error { } } + // send gitter notifications + if n.Gitter != nil { + err := n.Gitter.Send(context) + if err != nil { + log.Println(err) + } + } + // send email notifications // TODO (bradrydzewski) need to improve this code githubStatus := new(github.GitHub) @@ -77,3 +89,29 @@ func (n *Notification) Send(context *model.Request) error { return nil } + +func getBuildUrl(context *model.Request) string { + return fmt.Sprintf("%s/%s/%s/%s/%s/%s", context.Host, context.Repo.Host, context.Repo.Owner, context.Repo.Name, context.Commit.Branch, context.Commit.Sha) +} + +// helper fuction to sent HTTP Post requests +// with JSON data as the payload. +func sendJson(url string, payload []byte, headers map[string]string) { + client := &http.Client{} + buf := bytes.NewBuffer(payload) + + req, err := http.NewRequest("POST", url, buf) + + req.Header.Set("Content-Type", "application/json") + if headers != nil { + for k, v := range headers { + req.Header.Add(k, v) + } + } + + resp, err := client.Do(req) + if err != nil { + return + } + resp.Body.Close() +} diff --git a/plugin/notify/slack.go b/plugin/notify/slack.go index e02069d8..63c38d16 100644 --- a/plugin/notify/slack.go +++ b/plugin/notify/slack.go @@ -1,10 +1,8 @@ package notify import ( - "bytes" "encoding/json" "fmt" - "net/http" "github.com/drone/drone/shared/model" ) @@ -39,25 +37,21 @@ func (s *Slack) Send(context *model.Request) error { return nil } -func getBuildUrl(context *model.Request) string { - return fmt.Sprintf("%s/%s/%s/%s/%s/%s", context.Host, context.Repo.Host, context.Repo.Owner, context.Repo.Name, context.Commit.Branch, context.Commit.Sha) -} - -func getMessage(context *model.Request, message string) string { +func (s *Slack) getMessage(context *model.Request, message string) string { url := getBuildUrl(context) return fmt.Sprintf(message, context.Repo.Name, url, context.Commit.ShaShort(), context.Commit.Author) } func (s *Slack) sendStarted(context *model.Request) error { - return s.send(getMessage(context, slackStartedMessage)) + return s.send(s.getMessage(context, slackStartedMessage)) } func (s *Slack) sendSuccess(context *model.Request) error { - return s.send(getMessage(context, slackSuccessMessage)) + return s.send(s.getMessage(context, slackSuccessMessage)) } func (s *Slack) sendFailure(context *model.Request) error { - return s.send(getMessage(context, slackFailureMessage)) + return s.send(s.getMessage(context, slackFailureMessage)) } // helper function to send HTTP requests @@ -77,18 +71,8 @@ func (s *Slack) send(msg string) error { // send payload url := fmt.Sprintf(slackEndpoint, s.Team, s.Token) - go sendJson(url, payload) + + go sendJson(url, payload, nil) return nil } - -// helper fuction to sent HTTP Post requests -// with JSON data as the payload. -func sendJson(url string, payload []byte) { - buf := bytes.NewBuffer(payload) - resp, err := http.Post(url, "application/json", buf) - if err != nil { - return - } - resp.Body.Close() -}