custom notifier JSON/text, notifier interface update, added example service and failure.

pull/663/head
hunterlong 2020-06-15 00:46:27 -07:00
parent f2ebe6de9f
commit a9ef085024
29 changed files with 204 additions and 118 deletions

View File

@ -190,8 +190,8 @@ class Api {
return axios.post('api/notifier/' + data.method, data).then(response => (response.data)) return axios.post('api/notifier/' + data.method, data).then(response => (response.data))
} }
async notifier_test(data) { async notifier_test(data, notifier) {
return axios.post('api/notifier/' + data.method + '/test', data).then(response => (response.data)) return axios.post('api/notifier/' + notifier + '/test', data).then(response => (response.data))
} }
async renewApiKeys() { async renewApiKeys() {

View File

@ -10,7 +10,6 @@
</span> </span>
</div> </div>
<div class="card-body"> <div class="card-body">
<p class="small text-muted" v-html="notifier.description"/> <p class="small text-muted" v-html="notifier.description"/>
<div v-for="(form, index) in notifier.form" v-bind:key="index" class="form-group"> <div v-for="(form, index) in notifier.form" v-bind:key="index" class="form-group">
@ -65,23 +64,24 @@
</form> </form>
<div v-if="error && !success" class="card text-black-50 bg-white mb-3"> <div v-if="error || success" class="card text-black-50 bg-white mb-3">
<div class="card-body"> <div class="card-body">
<div v-if="error && !success" class="alert alert-danger col-12" role="alert"> <div v-if="error && !success" class="alert alert-danger col-12" role="alert">
{{error}}<p v-if="response">Response:<br>{{response}}</p> {{error}}<p v-if="response">Response:<br>{{response}}</p>
</div> </div>
<div v-if="success" class="alert alert-success col-12" role="alert"> <div v-if="success" class="alert alert-success col-12" role="alert">
{{notifier.title}} appears to be working! <span class="text-capitalize">{{notifier.title}}</span> appears to be working!
<p v-if="response">Response:<br>{{response}}</p>
</div> </div>
<h5>Response</h5>
<codemirror :value="response"/>
</div> </div>
</div> </div>
<div class="card text-black-50 bg-white mb-3"> <div class="card text-black-50 bg-white mb-3">
<div class="card-body"> <div class="card-body">
<div class="row"> <div class="row">
<div class="col-4 col-sm-4 mb-2 mb-sm-0 mt-2 mt-sm-0"> <div class="col-4 col-sm-4 mb-2 mb-sm-0 mt-2 mt-sm-0">
<button @click.prevent="saveNotifier" type="submit" class="btn btn-block text-capitalize btn-primary save-notifier"> <button @click.prevent="saveNotifier" type="submit" class="btn btn-block text-capitalize btn-primary save-notifier">
@ -89,11 +89,11 @@
</button> </button>
</div> </div>
<div class="col-4 col-md-4"> <div class="col-4 col-md-4">
<button @click.prevent="testNotifier" class="btn btn-outline-dark btn-block text-capitalize test-notifier"> <button @click.prevent="testNotifier('success')" class="btn btn-outline-dark btn-block text-capitalize test-notifier">
<i class="fa fa-vial"></i>{{loadingTest ? "Loading..." : "Test Success"}}</button> <i class="fa fa-vial"></i>{{loadingTest ? "Loading..." : "Test Success"}}</button>
</div> </div>
<div class="col-4 col-md-4"> <div class="col-4 col-md-4">
<button @click.prevent="testNotifier" class="btn btn-outline-dark btn-block text-capitalize test-notifier"> <button @click.prevent="testNotifier('failure')" class="btn btn-outline-dark btn-block text-capitalize test-notifier">
<i class="fa fa-vial"></i>{{loadingTest ? "Loading..." : "Test Failure"}}</button> <i class="fa fa-vial"></i>{{loadingTest ? "Loading..." : "Test Failure"}}</button>
</div> </div>
</div> </div>
@ -140,6 +140,7 @@ export default {
loadingTest: false, loadingTest: false,
error: null, error: null,
response: null, response: null,
request: null,
success: false, success: false,
saved: false, saved: false,
success_data: null, success_data: null,
@ -183,13 +184,6 @@ export default {
setTimeout(function() { setTimeout(function() {
cm.refresh(); cm.refresh();
},1); },1);
},
onCmFocus(cm) {
console.log('the editor is focused!', cm)
},
onCmCodeChange(newCode) {
console.log('this is new code', newCode)
this.success_data = newCode
}, },
async enableToggle() { async enableToggle() {
this.notifier.enabled = !!this.notifier.enabled this.notifier.enabled = !!this.notifier.enabled
@ -214,14 +208,13 @@ export default {
}); });
this.form.success_data = this.success_data this.form.success_data = this.success_data
this.form.failure_data = this.failure_data this.form.failure_data = this.failure_data
window.console.log(this.form)
await Api.notifier_save(this.form) await Api.notifier_save(this.form)
const notifiers = await Api.notifiers() const notifiers = await Api.notifiers()
await this.$store.commit('setNotifiers', notifiers) await this.$store.commit('setNotifiers', notifiers)
this.saved = true this.saved = true
this.loading = false this.loading = false
}, },
async testNotifier() { async testNotifier(method="success") {
this.success = false this.success = false
this.loadingTest = true this.loadingTest = true
this.form.method = this.notifier.method this.form.method = this.notifier.method
@ -233,7 +226,11 @@ export default {
} }
this.form[field] = val this.form[field] = val
}); });
const tested = await Api.notifier_test(this.form) let req = {
notifier: this.form,
method: method,
}
const tested = await Api.notifier_test(req, this.notifier.method)
if (tested.success) { if (tested.success) {
this.success = true this.success = true
} else { } else {

View File

@ -190,6 +190,5 @@ func DecodeJSON(r *http.Request, obj interface{}) error {
if err != nil { if err != nil {
return errors.DecodeJSON return errors.DecodeJSON
} }
defer r.Body.Close() return r.Body.Close()
return nil
} }

View File

@ -2,6 +2,7 @@ package handlers
import ( import (
"github.com/gorilla/mux" "github.com/gorilla/mux"
"github.com/statping/statping/types/failures"
"github.com/statping/statping/types/notifications" "github.com/statping/statping/types/notifications"
"github.com/statping/statping/types/services" "github.com/statping/statping/types/services"
"net/http" "net/http"
@ -56,21 +57,33 @@ func apiNotifierUpdateHandler(w http.ResponseWriter, r *http.Request) {
sendJsonAction(vars["notifier"], "update", w, r) sendJsonAction(vars["notifier"], "update", w, r)
} }
type testNotificationReq struct {
Method string `json:"method"`
Notification notifications.Notification `json:"notifier"`
}
func testNotificationHandler(w http.ResponseWriter, r *http.Request) { func testNotificationHandler(w http.ResponseWriter, r *http.Request) {
vars := mux.Vars(r) vars := mux.Vars(r)
notifer, err := notifications.Find(vars["notifier"]) _, err := notifications.Find(vars["notifier"])
if err != nil { if err != nil {
sendErrorJson(err, w, r) sendErrorJson(err, w, r)
return return
} }
if err := DecodeJSON(r, &notifer); err != nil { var req testNotificationReq
if err := DecodeJSON(r, &req); err != nil {
sendErrorJson(err, w, r) sendErrorJson(err, w, r)
return return
} }
notif := services.ReturnNotifier(notifer.Method) notif := services.ReturnNotifier(req.Notification.Method)
out, err := notif.OnTest()
var out string
if req.Method == "success" {
out, err = notif.OnSuccess(services.Example(true))
} else {
out, err = notif.OnFailure(services.Example(false), failures.Example())
}
resp := &notifierTestResp{ resp := &notifierTestResp{
Success: err == nil, Success: err == nil,

View File

@ -49,22 +49,22 @@ func runCommand(app string, cmd ...string) (string, string, error) {
} }
// OnSuccess for commandLine will trigger successful service // OnSuccess for commandLine will trigger successful service
func (c *commandLine) OnSuccess(s *services.Service) error { func (c *commandLine) OnSuccess(s *services.Service) (string, error) {
tmpl := ReplaceVars(c.SuccessData, s, nil) tmpl := ReplaceVars(c.SuccessData, s, nil)
_, _, err := runCommand(c.Host, tmpl) out, _, err := runCommand(c.Host, tmpl)
return err return out, err
} }
// OnFailure for commandLine will trigger failing service // OnFailure for commandLine will trigger failing service
func (c *commandLine) OnFailure(s *services.Service, f *failures.Failure) error { func (c *commandLine) OnFailure(s *services.Service, f *failures.Failure) (string, error) {
tmpl := ReplaceVars(c.FailureData, s, f) tmpl := ReplaceVars(c.FailureData, s, f)
_, _, err := runCommand(c.Host, tmpl) _, ouerr, err := runCommand(c.Host, tmpl)
return err return ouerr, err
} }
// OnTest for commandLine triggers when this notifier has been saved // OnTest for commandLine triggers when this notifier has been saved
func (c *commandLine) OnTest() (string, error) { func (c *commandLine) OnTest() (string, error) {
tmpl := ReplaceVars(c.Var1, exampleService, exampleFailure) tmpl := ReplaceVars(c.Var1, services.Example(true), exampleFailure)
in, out, err := runCommand(c.Host, tmpl) in, out, err := runCommand(c.Host, tmpl)
utils.Log.Infoln(in) utils.Log.Infoln(in)
utils.Log.Infoln(out) utils.Log.Infoln(out)

View File

@ -39,12 +39,12 @@ func TestCommandNotifier(t *testing.T) {
}) })
t.Run("Command OnFailure", func(t *testing.T) { t.Run("Command OnFailure", func(t *testing.T) {
err := Command.OnFailure(exampleService, exampleFailure) _, err := Command.OnFailure(exampleService, exampleFailure)
assert.Nil(t, err) assert.Nil(t, err)
}) })
t.Run("Command OnSuccess", func(t *testing.T) { t.Run("Command OnSuccess", func(t *testing.T) {
err := Command.OnSuccess(exampleService) _, err := Command.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })

View File

@ -41,9 +41,9 @@ var Discorder = &discord{&notifications.Notification{
} }
// Send will send a HTTP Post to the discord API. It accepts type: []byte // Send will send a HTTP Post to the discord API. It accepts type: []byte
func (d *discord) sendRequest(msg string) error { func (d *discord) sendRequest(msg string) (string, error) {
_, _, err := utils.HttpRequest(Discorder.GetValue("host"), "POST", "application/json", nil, strings.NewReader(msg), time.Duration(10*time.Second), true, nil) out, _, err := utils.HttpRequest(Discorder.GetValue("host"), "POST", "application/json", nil, strings.NewReader(msg), time.Duration(10*time.Second), true, nil)
return err return string(out), err
} }
func (d *discord) Select() *notifications.Notification { func (d *discord) Select() *notifications.Notification {
@ -51,15 +51,17 @@ func (d *discord) Select() *notifications.Notification {
} }
// OnFailure will trigger failing service // OnFailure will trigger failing service
func (d *discord) OnFailure(s *services.Service, f *failures.Failure) error { func (d *discord) OnFailure(s *services.Service, f *failures.Failure) (string, error) {
msg := `{"content": "Your service '{{.Service.Name}}' is currently failing! Reason: {{.Failure.Issue}}"}` msg := `{"content": "Your service '{{.Service.Name}}' is currently failing! Reason: {{.Failure.Issue}}"}`
return d.sendRequest(ReplaceVars(msg, s, f)) out, err := d.sendRequest(ReplaceVars(msg, s, f))
return out, err
} }
// OnSuccess will trigger successful service // OnSuccess will trigger successful service
func (d *discord) OnSuccess(s *services.Service) error { func (d *discord) OnSuccess(s *services.Service) (string, error) {
msg := `{"content": "Your service '{{.Service.Name}}' is currently online!"}` msg := `{"content": "Your service '{{.Service.Name}}' is currently online!"}`
return d.sendRequest(ReplaceVars(msg, s, nil)) out, err := d.sendRequest(ReplaceVars(msg, s, nil))
return out, err
} }
// OnSave triggers when this notifier has been saved // OnSave triggers when this notifier has been saved

View File

@ -46,12 +46,12 @@ func TestDiscordNotifier(t *testing.T) {
}) })
t.Run("discord OnFailure", func(t *testing.T) { t.Run("discord OnFailure", func(t *testing.T) {
err := Discorder.OnFailure(exampleService, exampleFailure) _, err := Discorder.OnFailure(exampleService, exampleFailure)
assert.Nil(t, err) assert.Nil(t, err)
}) })
t.Run("discord OnSuccess", func(t *testing.T) { t.Run("discord OnSuccess", func(t *testing.T) {
err := Discorder.OnSuccess(exampleService) _, err := Discorder.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })

View File

@ -164,7 +164,7 @@ type emailOutgoing struct {
} }
// OnFailure will trigger failing service // OnFailure will trigger failing service
func (e *emailer) OnFailure(s *services.Service, f *failures.Failure) error { func (e *emailer) OnFailure(s *services.Service, f *failures.Failure) (string, error) {
subject := fmt.Sprintf("Service %s is Offline", s.Name) subject := fmt.Sprintf("Service %s is Offline", s.Name)
email := &emailOutgoing{ email := &emailOutgoing{
To: e.Var2, To: e.Var2,
@ -176,11 +176,11 @@ func (e *emailer) OnFailure(s *services.Service, f *failures.Failure) error {
}, },
From: e.Var1, From: e.Var1,
} }
return e.dialSend(email) return "email failed", e.dialSend(email)
} }
// OnSuccess will trigger successful service // OnSuccess will trigger successful service
func (e *emailer) OnSuccess(s *services.Service) error { func (e *emailer) OnSuccess(s *services.Service) (string, error) {
subject := fmt.Sprintf("Service %s is Back Online", s.Name) subject := fmt.Sprintf("Service %s is Back Online", s.Name)
email := &emailOutgoing{ email := &emailOutgoing{
To: e.Var2, To: e.Var2,
@ -192,7 +192,7 @@ func (e *emailer) OnSuccess(s *services.Service) error {
}, },
From: e.Var1, From: e.Var1,
} }
return e.dialSend(email) return "email sent", e.dialSend(email)
} }
// OnTest triggers when this notifier has been saved // OnTest triggers when this notifier has been saved

View File

@ -62,12 +62,12 @@ func TestEmailNotifier(t *testing.T) {
}) })
t.Run("email OnFailure", func(t *testing.T) { t.Run("email OnFailure", func(t *testing.T) {
err := email.OnFailure(exampleService, exampleFailure) _, err := email.OnFailure(exampleService, exampleFailure)
assert.Nil(t, err) assert.Nil(t, err)
}) })
t.Run("email OnSuccess", func(t *testing.T) { t.Run("email OnSuccess", func(t *testing.T) {
err := email.OnSuccess(exampleService) _, err := email.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })
@ -76,7 +76,7 @@ func TestEmailNotifier(t *testing.T) {
}) })
t.Run("email OnSuccess Again", func(t *testing.T) { t.Run("email OnSuccess Again", func(t *testing.T) {
err := email.OnSuccess(exampleService) _, err := email.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })

View File

@ -52,17 +52,17 @@ func (l *lineNotifier) sendMessage(message string) (string, error) {
} }
// OnFailure will trigger failing service // OnFailure will trigger failing service
func (l *lineNotifier) OnFailure(s *services.Service, f *failures.Failure) error { func (l *lineNotifier) OnFailure(s *services.Service, f *failures.Failure) (string, error) {
msg := fmt.Sprintf("Your service '%v' is currently offline!", s.Name) msg := fmt.Sprintf("Your service '%v' is currently offline!", s.Name)
_, err := l.sendMessage(msg) out, err := l.sendMessage(msg)
return err return out, err
} }
// OnSuccess will trigger successful service // OnSuccess will trigger successful service
func (l *lineNotifier) OnSuccess(s *services.Service) error { func (l *lineNotifier) OnSuccess(s *services.Service) (string, error) {
msg := fmt.Sprintf("Service %s is online!", s.Name) msg := fmt.Sprintf("Service %s is online!", s.Name)
_, err := l.sendMessage(msg) out, err := l.sendMessage(msg)
return err return out, err
} }
// OnTest triggers when this notifier has been saved // OnTest triggers when this notifier has been saved

View File

@ -71,18 +71,18 @@ func dataJson(s *services.Service, f *failures.Failure) map[string]interface{} {
} }
// OnFailure will trigger failing service // OnFailure will trigger failing service
func (m *mobilePush) OnFailure(s *services.Service, f *failures.Failure) error { func (m *mobilePush) OnFailure(s *services.Service, f *failures.Failure) (string, error) {
data := dataJson(s, f) data := dataJson(s, f)
msg := &pushArray{ msg := &pushArray{
Message: fmt.Sprintf("Your service '%v' is currently failing! Reason: %v", s.Name, f.Issue), Message: fmt.Sprintf("Your service '%v' is currently failing! Reason: %v", s.Name, f.Issue),
Title: "Service Offline", Title: "Service Offline",
Data: data, Data: data,
} }
return m.Send(msg) return "notification sent", m.Send(msg)
} }
// OnSuccess will trigger successful service // OnSuccess will trigger successful service
func (m *mobilePush) OnSuccess(s *services.Service) error { func (m *mobilePush) OnSuccess(s *services.Service) (string, error) {
data := dataJson(s, nil) data := dataJson(s, nil)
msg := &pushArray{ msg := &pushArray{
Message: "Service is Online!", Message: "Service is Online!",
@ -90,7 +90,7 @@ func (m *mobilePush) OnSuccess(s *services.Service) error {
Data: data, Data: data,
Platform: 2, Platform: 2,
} }
return m.Send(msg) return "notification sent", m.Send(msg)
} }
// OnTest triggers when this notifier has been saved // OnTest triggers when this notifier has been saved

View File

@ -51,12 +51,12 @@ func TestMobileNotifier(t *testing.T) {
}) })
t.Run("Mobile OnFailure", func(t *testing.T) { t.Run("Mobile OnFailure", func(t *testing.T) {
err := Mobile.OnFailure(exampleService, exampleFailure) _, err := Mobile.OnFailure(exampleService, exampleFailure)
assert.Nil(t, err) assert.Nil(t, err)
}) })
t.Run("Mobile OnSuccess", func(t *testing.T) { t.Run("Mobile OnSuccess", func(t *testing.T) {
err := Mobile.OnSuccess(exampleService) _, err := Mobile.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })

View File

@ -12,6 +12,7 @@ import (
) )
var log = utils.Log.WithField("type", "notifier") var log = utils.Log.WithField("type", "notifier")
var exampleService = services.Example(true)
type replacer struct { type replacer struct {
Core *core.Core Core *core.Core
@ -62,7 +63,7 @@ func ReplaceVars(input string, s *services.Service, f *failures.Failure) string
return ReplaceTemplate(input, replacer{Service: s, Failure: f, Core: core.App}) return ReplaceTemplate(input, replacer{Service: s, Failure: f, Core: core.App})
} }
var exampleService = &services.Service{ var ExampleService = &services.Service{
Id: 1, Id: 1,
Name: "Statping", Name: "Statping",
Domain: "https://statping.com", Domain: "https://statping.com",

View File

@ -70,22 +70,23 @@ func (t *pushover) sendMessage(message string) (string, error) {
} }
// OnFailure will trigger failing service // OnFailure will trigger failing service
func (t *pushover) OnFailure(s *services.Service, f *failures.Failure) error { func (t *pushover) OnFailure(s *services.Service, f *failures.Failure) (string, error) {
message := ReplaceVars(t.FailureData, s, f) message := ReplaceVars(t.FailureData, s, f)
_, err := t.sendMessage(message) out, err := t.sendMessage(message)
return err return out, err
} }
// OnSuccess will trigger successful service // OnSuccess will trigger successful service
func (t *pushover) OnSuccess(s *services.Service) error { func (t *pushover) OnSuccess(s *services.Service) (string, error) {
message := ReplaceVars(t.SuccessData, s, nil) message := ReplaceVars(t.SuccessData, s, nil)
_, err := t.sendMessage(message) out, err := t.sendMessage(message)
return err return out, err
} }
// OnTest will test the Pushover SMS messaging // OnTest will test the Pushover SMS messaging
func (t *pushover) OnTest() (string, error) { func (t *pushover) OnTest() (string, error) {
msg := fmt.Sprintf("Testing the Pushover Notifier, Your service '%s' is currently offline! Error: %s", exampleService.Name, exampleFailure.Issue) example := services.Example(true)
msg := fmt.Sprintf("Testing the Pushover Notifier, Your service '%s' is currently offline! Error: %s", example.Name, exampleFailure.Issue)
content, err := t.sendMessage(msg) content, err := t.sendMessage(msg)
return content, err return content, err
} }

View File

@ -49,12 +49,12 @@ func TestPushoverNotifier(t *testing.T) {
}) })
t.Run("Pushover OnFailure", func(t *testing.T) { t.Run("Pushover OnFailure", func(t *testing.T) {
err := Pushover.OnFailure(exampleService, exampleFailure) _, err := Pushover.OnFailure(exampleService, exampleFailure)
assert.Nil(t, err) assert.Nil(t, err)
}) })
t.Run("Pushover OnSuccess", func(t *testing.T) { t.Run("Pushover OnSuccess", func(t *testing.T) {
err := Pushover.OnSuccess(exampleService) _, err := Pushover.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })

View File

@ -56,17 +56,17 @@ var slacker = &slack{&notifications.Notification{
} }
// Send will send a HTTP Post to the slack webhooker API. It accepts type: string // Send will send a HTTP Post to the slack webhooker API. It accepts type: string
func (s *slack) sendSlack(msg string) error { func (s *slack) sendSlack(msg string) (string, error) {
_, resp, err := utils.HttpRequest(s.Host, "POST", "application/json", nil, strings.NewReader(msg), time.Duration(10*time.Second), true, nil) resp, _, err := utils.HttpRequest(s.Host, "POST", "application/json", nil, strings.NewReader(msg), time.Duration(10*time.Second), true, nil)
if err != nil { if err != nil {
return err return "", err
} }
defer resp.Body.Close() return string(resp), nil
return nil
} }
func (s *slack) OnTest() (string, error) { func (s *slack) OnTest() (string, error) {
testMsg := ReplaceVars(failingTemplate, exampleService, exampleFailure) example := services.Example(true)
testMsg := ReplaceVars(failingTemplate, example, nil)
contents, resp, err := utils.HttpRequest(s.Host, "POST", "application/json", nil, bytes.NewBuffer([]byte(testMsg)), time.Duration(10*time.Second), true, nil) contents, resp, err := utils.HttpRequest(s.Host, "POST", "application/json", nil, bytes.NewBuffer([]byte(testMsg)), time.Duration(10*time.Second), true, nil)
if err != nil { if err != nil {
return "", err return "", err
@ -79,13 +79,15 @@ func (s *slack) OnTest() (string, error) {
} }
// OnFailure will trigger failing service // OnFailure will trigger failing service
func (s *slack) OnFailure(srv *services.Service, f *failures.Failure) error { func (s *slack) OnFailure(srv *services.Service, f *failures.Failure) (string, error) {
msg := ReplaceVars(failingTemplate, srv, f) msg := ReplaceVars(failingTemplate, srv, f)
return s.sendSlack(msg) out, err := s.sendSlack(msg)
return out, err
} }
// OnSuccess will trigger successful service // OnSuccess will trigger successful service
func (s *slack) OnSuccess(srv *services.Service) error { func (s *slack) OnSuccess(srv *services.Service) (string, error) {
msg := ReplaceVars(successTemplate, srv, nil) msg := ReplaceVars(successTemplate, srv, nil)
return s.sendSlack(msg) out, err := s.sendSlack(msg)
return out, err
} }

View File

@ -47,12 +47,12 @@ func TestSlackNotifier(t *testing.T) {
}) })
t.Run("slack OnFailure", func(t *testing.T) { t.Run("slack OnFailure", func(t *testing.T) {
err := slacker.OnFailure(exampleService, exampleFailure) _, err := slacker.OnFailure(exampleService, exampleFailure)
assert.Nil(t, err) assert.Nil(t, err)
}) })
t.Run("slack OnSuccess", func(t *testing.T) { t.Run("slack OnSuccess", func(t *testing.T) {
err := slacker.OnSuccess(exampleService) _, err := slacker.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })

View File

@ -74,17 +74,17 @@ func (t *telegram) sendMessage(message string) (string, error) {
} }
// OnFailure will trigger failing service // OnFailure will trigger failing service
func (t *telegram) OnFailure(s *services.Service, f *failures.Failure) error { func (t *telegram) OnFailure(s *services.Service, f *failures.Failure) (string, error) {
msg := ReplaceVars(t.FailureData, s, f) msg := ReplaceVars(t.FailureData, s, f)
_, err := t.sendMessage(msg) out, err := t.sendMessage(msg)
return err return out, err
} }
// OnSuccess will trigger successful service // OnSuccess will trigger successful service
func (t *telegram) OnSuccess(s *services.Service) error { func (t *telegram) OnSuccess(s *services.Service) (string, error) {
msg := ReplaceVars(t.SuccessData, s, nil) msg := ReplaceVars(t.SuccessData, s, nil)
_, err := t.sendMessage(msg) out, err := t.sendMessage(msg)
return err return out, err
} }
// OnTest will test the Twilio SMS messaging // OnTest will test the Twilio SMS messaging

View File

@ -53,12 +53,12 @@ func TestTelegramNotifier(t *testing.T) {
}) })
t.Run("Telegram OnFailure", func(t *testing.T) { t.Run("Telegram OnFailure", func(t *testing.T) {
err := Telegram.OnFailure(exampleService, exampleFailure) _, err := Telegram.OnFailure(exampleService, exampleFailure)
assert.Nil(t, err) assert.Nil(t, err)
}) })
t.Run("Telegram OnSuccess", func(t *testing.T) { t.Run("Telegram OnSuccess", func(t *testing.T) {
err := Telegram.OnSuccess(exampleService) _, err := Telegram.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })

View File

@ -90,17 +90,15 @@ func (t *twilio) sendMessage(message string) (string, error) {
} }
// OnFailure will trigger failing service // OnFailure will trigger failing service
func (t *twilio) OnFailure(s *services.Service, f *failures.Failure) error { func (t *twilio) OnFailure(s *services.Service, f *failures.Failure) (string, error) {
msg := ReplaceVars(t.FailureData, s, f) msg := ReplaceVars(t.FailureData, s, f)
_, err := t.sendMessage(msg) return t.sendMessage(msg)
return err
} }
// OnSuccess will trigger successful service // OnSuccess will trigger successful service
func (t *twilio) OnSuccess(s *services.Service) error { func (t *twilio) OnSuccess(s *services.Service) (string, error) {
msg := ReplaceVars(t.SuccessData, s, nil) msg := ReplaceVars(t.SuccessData, s, nil)
_, err := t.sendMessage(msg) return t.sendMessage(msg)
return err
} }
// OnTest will test the Twilio SMS messaging // OnTest will test the Twilio SMS messaging

View File

@ -53,12 +53,12 @@ func TestTwilioNotifier(t *testing.T) {
}) })
t.Run("Twilio OnFailure", func(t *testing.T) { t.Run("Twilio OnFailure", func(t *testing.T) {
err := Twilio.OnFailure(exampleService, exampleFailure) _, err := Twilio.OnFailure(exampleService, exampleFailure)
assert.Nil(t, err) assert.Nil(t, err)
}) })
t.Run("Twilio OnSuccess", func(t *testing.T) { t.Run("Twilio OnSuccess", func(t *testing.T) {
err := Twilio.OnSuccess(exampleService) _, err := Twilio.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })

View File

@ -111,7 +111,9 @@ func (w *webhooker) sendHttpWebhook(body string) (*http.Response, error) {
} }
func (w *webhooker) OnTest() (string, error) { func (w *webhooker) OnTest() (string, error) {
body := ReplaceVars(w.SuccessData, exampleService, exampleFailure) f := failures.Example()
s := services.Example(false)
body := ReplaceVars(w.SuccessData, s, f)
resp, err := w.sendHttpWebhook(body) resp, err := w.sendHttpWebhook(body)
if err != nil { if err != nil {
return "", err return "", err
@ -124,23 +126,25 @@ func (w *webhooker) OnTest() (string, error) {
} }
// OnFailure will trigger failing service // OnFailure will trigger failing service
func (w *webhooker) OnFailure(s *services.Service, f *failures.Failure) error { func (w *webhooker) OnFailure(s *services.Service, f *failures.Failure) (string, error) {
msg := ReplaceVars(w.FailureData, s, f) msg := ReplaceVars(w.FailureData, s, f)
resp, err := w.sendHttpWebhook(msg) resp, err := w.sendHttpWebhook(msg)
if err != nil { if err != nil {
return err return "", err
} }
defer resp.Body.Close() defer resp.Body.Close()
return err content, err := ioutil.ReadAll(resp.Body)
return string(content), err
} }
// OnSuccess will trigger successful service // OnSuccess will trigger successful service
func (w *webhooker) OnSuccess(s *services.Service) error { func (w *webhooker) OnSuccess(s *services.Service) (string, error) {
msg := ReplaceVars(w.SuccessData, s, nil) msg := ReplaceVars(w.SuccessData, s, nil)
resp, err := w.sendHttpWebhook(msg) resp, err := w.sendHttpWebhook(msg)
if err != nil { if err != nil {
return err return "", err
} }
defer resp.Body.Close() defer resp.Body.Close()
return err content, err := ioutil.ReadAll(resp.Body)
return string(content), err
} }

View File

@ -45,12 +45,12 @@ func TestWebhookNotifier(t *testing.T) {
}) })
t.Run("webhooker OnFailure", func(t *testing.T) { t.Run("webhooker OnFailure", func(t *testing.T) {
err := Webhook.OnFailure(exampleService, exampleFailure) _, err := Webhook.OnFailure(exampleService, exampleFailure)
assert.Nil(t, err) assert.Nil(t, err)
}) })
t.Run("webhooker OnSuccess", func(t *testing.T) { t.Run("webhooker OnSuccess", func(t *testing.T) {
err := Webhook.OnSuccess(exampleService) _, err := Webhook.OnSuccess(exampleService)
assert.Nil(t, err) assert.Nil(t, err)
}) })

View File

@ -12,6 +12,20 @@ var (
log = utils.Log.WithField("type", "failure") log = utils.Log.WithField("type", "failure")
) )
func Example() *Failure {
return &Failure{
Id: 48533,
Issue: "Response did not response a 200 status code",
Method: "",
MethodId: 0,
ErrorCode: 404,
Service: 1,
Checkin: 0,
PingTime: 48309,
CreatedAt: utils.Now(),
}
}
func Samples() error { func Samples() error {
log.Infoln("Inserting Sample Service Failures...") log.Infoln("Inserting Sample Service Failures...")
createdAt := utils.Now().Add(-3 * types.Day) createdAt := utils.Now().Add(-3 * types.Day)

View File

@ -7,7 +7,7 @@ import (
// Notifier interface is required to create a new Notifier // Notifier interface is required to create a new Notifier
type Notifier interface { type Notifier interface {
OnSuccess(*services.Service) error // OnSuccess is triggered when a service is successful OnSuccess(*services.Service) (string, error) // OnSuccess is triggered when a service is successful
OnFailure(*services.Service, *failures.Failure) error // OnFailure is triggered when a service is failing OnFailure(*services.Service, *failures.Failure) (string, error) // OnFailure is triggered when a service is failing
OnTest() (string, error) // OnTest is triggered for testing OnTest() (string, error) // OnTest is triggered for testing
} }

View File

@ -26,8 +26,8 @@ func FindNotifier(method string) *notifications.Notification {
} }
type ServiceNotifier interface { type ServiceNotifier interface {
OnSuccess(*Service) error // OnSuccess is triggered when a service is successful OnSuccess(*Service) (string, error) // OnSuccess is triggered when a service is successful
OnFailure(*Service, *failures.Failure) error // OnFailure is triggered when a service is failing OnFailure(*Service, *failures.Failure) (string, error) // OnFailure is triggered when a service is failing
OnTest() (string, error) // OnTest is triggered for testing OnTest() (string, error) // OnTest is triggered for testing
Select() *notifications.Notification // OnTest is triggered for testing Select() *notifications.Notification // OnTest is triggered for testing
} }

View File

@ -343,7 +343,7 @@ func sendSuccess(s *Service) {
notif := n.Select() notif := n.Select()
if notif.CanSend() { if notif.CanSend() {
log.Infof("Sending notification to: %s!", notif.Method) log.Infof("Sending notification to: %s!", notif.Method)
if err := n.OnSuccess(s); err != nil { if _, err := n.OnSuccess(s); err != nil {
notif.Logger().Errorln(err) notif.Logger().Errorln(err)
} }
s.UserNotified = true s.UserNotified = true
@ -394,7 +394,7 @@ func sendFailure(s *Service, f *failures.Failure) {
notif := n.Select() notif := n.Select()
if notif.CanSend() { if notif.CanSend() {
log.Infof("Sending Failure notification to: %s!", notif.Method) log.Infof("Sending Failure notification to: %s!", notif.Method)
if err := n.OnFailure(s, f); err != nil { if _, err := n.OnFailure(s, f); err != nil {
notif.Logger().WithField("failure", f.Issue).Errorln(err) notif.Logger().WithField("failure", f.Issue).Errorln(err)
} }
s.UserNotified = true s.UserNotified = true

View File

@ -6,6 +6,61 @@ import (
"time" "time"
) )
func Example(online bool) *Service {
return &Service{
Id: 6283,
Name: "Statping Example",
Domain: "https://localhost:8080",
Expected: null.NewNullString(""),
ExpectedStatus: 200,
Interval: int(time.Duration(15 * time.Second).Seconds()),
Type: "http",
Method: "get",
PostData: null.NullString{},
Port: 0,
Timeout: int(time.Duration(2 * time.Second).Seconds()),
Order: 0,
VerifySSL: null.NewNullBool(true),
Public: null.NewNullBool(true),
GroupId: 0,
TLSCert: null.NullString{},
TLSCertKey: null.NullString{},
TLSCertRoot: null.NullString{},
Headers: null.NullString{},
Permalink: null.NewNullString("example-service"),
Redirect: null.NewNullBool(true),
CreatedAt: utils.Now().Add(-23 * time.Hour),
UpdatedAt: utils.Now().Add(-23 * time.Hour),
Online: online,
Latency: 393443,
PingTime: 83526,
Online24Hours: 0.98,
Online7Days: 0.99,
AvgResponse: 303443,
FailuresLast24Hours: 2,
Checkpoint: time.Time{},
SleepDuration: 5 * time.Second,
LastResponse: "The example service is hitting this page",
NotifyAfter: 0,
notifyAfterCount: 0,
AllowNotifications: null.NewNullBool(true),
UserNotified: false,
UpdateNotify: null.NewNullBool(true),
DownText: "The service ws responding with 500 status code",
SuccessNotified: false,
LastStatusCode: 200,
Failures: nil,
AllCheckins: nil,
LastLookupTime: 4600,
LastLatency: 124399,
LastCheck: utils.Now().Add(-37 * time.Second),
LastOnline: utils.Now().Add(-37 * time.Second),
LastOffline: utils.Now().Add((-14 * 24) * time.Hour),
SecondsOnline: int64(utils.Now().Add(-24 * time.Hour).Second()),
SecondsOffline: int64(utils.Now().Add(-150 * time.Second).Second()),
}
}
func Samples() error { func Samples() error {
log.Infoln("Inserting Sample Services...") log.Infoln("Inserting Sample Services...")
createdOn := utils.Now().Add(((-24 * 30) * 3) * time.Hour) createdOn := utils.Now().Add(((-24 * 30) * 3) * time.Hour)