[IMP] Error Handling and Tests
Signed-off-by: David Arnold <dar@devco.co>
This commit is contained in:
parent
8e2b6ea996
commit
8ee442042e
|
@ -1,3 +1,5 @@
|
||||||
|
// Package uwsgi implements a telegraf plugin for
|
||||||
|
// collecting uwsgi stats from the uwsgi stats server.
|
||||||
package uwsgi
|
package uwsgi
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
@ -15,14 +17,53 @@ import (
|
||||||
|
|
||||||
var timeout = 5 * time.Second
|
var timeout = 5 * time.Second
|
||||||
|
|
||||||
|
// uWSGI Server struct
|
||||||
type Uwsgi struct {
|
type Uwsgi struct {
|
||||||
Servers []string `toml:"server"`
|
Servers []string `toml:"server"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Errors is a list of errors accumulated during an interval.
|
||||||
|
type Errors []error
|
||||||
|
|
||||||
|
func (errs Errors) Error() string {
|
||||||
|
s := ""
|
||||||
|
for _, err := range errs {
|
||||||
|
if s == "" {
|
||||||
|
s = err.Error()
|
||||||
|
} else {
|
||||||
|
s = s + ". " + err.Error()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
// NestedError wraps an error returned from deeper in the code.
|
||||||
|
type NestedError struct {
|
||||||
|
// Err is the error from where the NestedError was constructed.
|
||||||
|
Err error
|
||||||
|
// NestedError is the error that was passed back from the called function.
|
||||||
|
NestedErr error
|
||||||
|
}
|
||||||
|
|
||||||
|
// Error returns a concatenated string of all the nested errors.
|
||||||
|
func (ne NestedError) Error() string {
|
||||||
|
return ne.Err.Error() + ": " + ne.NestedErr.Error()
|
||||||
|
}
|
||||||
|
|
||||||
|
// Errorf is a convenience function for constructing a NestedError.
|
||||||
|
func Errorf(err error, msg string, format ...interface{}) error {
|
||||||
|
return NestedError{
|
||||||
|
NestedErr: err,
|
||||||
|
Err: fmt.Errorf(msg, format...),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Description returns the plugin description
|
||||||
func (u *Uwsgi) Description() string {
|
func (u *Uwsgi) Description() string {
|
||||||
return "Read uWSGI metrics."
|
return "Read uWSGI metrics."
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// SampleConfig returns the sample configuration
|
||||||
func (u *Uwsgi) SampleConfig() string {
|
func (u *Uwsgi) SampleConfig() string {
|
||||||
return `
|
return `
|
||||||
## List with urls of uWSGI Stats servers. Url must match pattern:
|
## List with urls of uWSGI Stats servers. Url must match pattern:
|
||||||
|
@ -34,17 +75,20 @@ func (u *Uwsgi) SampleConfig() string {
|
||||||
`
|
`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Gather collect data from uWSGI Server
|
||||||
func (u *Uwsgi) Gather(acc telegraf.Accumulator) error {
|
func (u *Uwsgi) Gather(acc telegraf.Accumulator) error {
|
||||||
|
var errs Errors
|
||||||
for _, s := range u.Servers {
|
for _, s := range u.Servers {
|
||||||
n, err := url.Parse(s)
|
n, err := url.Parse(s)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fmt.Errorf("Could not parse uWSGI Stats Server url '%s': %s", s, err)
|
return fmt.Errorf("Could not parse uWSGI Stats Server url '%s': %s", s, err)
|
||||||
}
|
}
|
||||||
|
if err := u.gatherServer(acc, n); err != nil {
|
||||||
u.gatherServer(acc, n)
|
errs = append(errs, Errorf(err, "server %s", s))
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
return nil
|
return errs
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *Uwsgi) gatherServer(acc telegraf.Accumulator, url *url.URL) error {
|
func (u *Uwsgi) gatherServer(acc telegraf.Accumulator, url *url.URL) error {
|
||||||
|
@ -59,7 +103,7 @@ func (u *Uwsgi) gatherServer(acc telegraf.Accumulator, url *url.URL) error {
|
||||||
case "http":
|
case "http":
|
||||||
resp, err := http.Get(url.String())
|
resp, err := http.Get(url.String())
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fmt.Errorf("Could not connect to uWSGI Stats Server '%s': %s", url.String(), err)
|
return Errorf(err, "Could not connect to uWSGI Stats Server '%s'", url.String())
|
||||||
}
|
}
|
||||||
r = resp.Body
|
r = resp.Body
|
||||||
default:
|
default:
|
||||||
|
@ -67,7 +111,7 @@ func (u *Uwsgi) gatherServer(acc telegraf.Accumulator, url *url.URL) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return fmt.Errorf("Could not connect to uWSGI Stats Server '%s': %s", url.String(), err)
|
return Errorf(err, "Could not connect to uWSGI Stats Server '%s'", url.String())
|
||||||
}
|
}
|
||||||
defer r.Close()
|
defer r.Close()
|
||||||
|
|
||||||
|
@ -75,11 +119,13 @@ func (u *Uwsgi) gatherServer(acc telegraf.Accumulator, url *url.URL) error {
|
||||||
s.Url = url.String()
|
s.Url = url.String()
|
||||||
|
|
||||||
dec := json.NewDecoder(r)
|
dec := json.NewDecoder(r)
|
||||||
dec.Decode(&s)
|
if err := dec.Decode(&s); err != nil {
|
||||||
|
return Errorf(err, "Could not decode json payload from server '%s'", url.String())
|
||||||
|
}
|
||||||
|
|
||||||
u.gatherStatServer(acc, &s)
|
u.gatherStatServer(acc, &s)
|
||||||
|
|
||||||
return nil
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
func (u *Uwsgi) gatherStatServer(acc telegraf.Accumulator, s *StatsServer) {
|
func (u *Uwsgi) gatherStatServer(acc telegraf.Accumulator, s *StatsServer) {
|
||||||
|
|
|
@ -123,3 +123,57 @@ func TestBasic(t *testing.T) {
|
||||||
var acc testutil.Accumulator
|
var acc testutil.Accumulator
|
||||||
require.NoError(t, plugin.Gather(&acc))
|
require.NoError(t, plugin.Gather(&acc))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestInvalidJason(t *testing.T) {
|
||||||
|
js := `
|
||||||
|
{
|
||||||
|
"version":"2.0.12",
|
||||||
|
"listen_queue":0,
|
||||||
|
"listen_queue_errors":0,
|
||||||
|
"signal_queue":0,
|
||||||
|
"load":0,
|
||||||
|
"pid:28372
|
||||||
|
"uid":10
|
||||||
|
}
|
||||||
|
`
|
||||||
|
|
||||||
|
fakeServer := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
if r.URL.Path == "/" {
|
||||||
|
_, _ = w.Write([]byte(js))
|
||||||
|
} else {
|
||||||
|
w.WriteHeader(http.StatusNotFound)
|
||||||
|
}
|
||||||
|
}))
|
||||||
|
|
||||||
|
defer fakeServer.Close()
|
||||||
|
|
||||||
|
plugin := &uwsgi.Uwsgi{
|
||||||
|
Servers: []string{fakeServer.URL + "/"},
|
||||||
|
}
|
||||||
|
var acc testutil.Accumulator
|
||||||
|
require.Error(t, plugin.Gather(&acc))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestHttpError(t *testing.T) {
|
||||||
|
plugin := &uwsgi.Uwsgi{
|
||||||
|
Servers: []string{"http://novalidurladress/"},
|
||||||
|
}
|
||||||
|
var acc testutil.Accumulator
|
||||||
|
require.Error(t, plugin.Gather(&acc))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestTcpError(t *testing.T) {
|
||||||
|
plugin := &uwsgi.Uwsgi{
|
||||||
|
Servers: []string{"tcp://novalidtcpadress/"},
|
||||||
|
}
|
||||||
|
var acc testutil.Accumulator
|
||||||
|
require.Error(t, plugin.Gather(&acc))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestUnixSocketError(t *testing.T) {
|
||||||
|
plugin := &uwsgi.Uwsgi{
|
||||||
|
Servers: []string{"unix:///novalidunixsocket"},
|
||||||
|
}
|
||||||
|
var acc testutil.Accumulator
|
||||||
|
require.Error(t, plugin.Gather(&acc))
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in New Issue