From 1c73caba04c854933a96b0becd1d32ddf313ec14 Mon Sep 17 00:00:00 2001 From: Bob Shannon Date: Wed, 7 Jun 2017 20:52:10 -0400 Subject: [PATCH] Add SSL/TLS support to nginx input plugin (#2883) --- CHANGELOG.md | 1 + plugins/inputs/nginx/README.md | 10 ++++++ plugins/inputs/nginx/nginx.go | 63 +++++++++++++++++++++++++++++----- 3 files changed, 65 insertions(+), 9 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index dcabd7d7d..2216e6a8f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,7 @@ - [#2773](https://github.com/influxdata/telegraf/pull/2773): Add support for self-signed certs to InfluxDB input plugin - [#2581](https://github.com/influxdata/telegraf/pull/2581): Add Docker container environment variables as tags. Only whitelisted - [#2817](https://github.com/influxdata/telegraf/pull/2817): Added timeout option to IPMI sensor plugin +- [#2883](https://github.com/influxdata/telegraf/pull/2883): Add support for an optional SSL/TLS configuration to nginx input plugin - [#2882](https://github.com/influxdata/telegraf/pull/2882): Add timezone support for logparser timestamps. - [#2814](https://github.com/influxdata/telegraf/pull/2814): Add result_type field for http_response input. diff --git a/plugins/inputs/nginx/README.md b/plugins/inputs/nginx/README.md index dab54329b..819501ea7 100644 --- a/plugins/inputs/nginx/README.md +++ b/plugins/inputs/nginx/README.md @@ -7,6 +7,16 @@ [[inputs.nginx]] ## An array of Nginx stub_status URI to gather stats. urls = ["http://localhost/server_status"] + + ## Optional SSL Config + # ssl_ca = "/etc/telegraf/ca.pem" + # ssl_cert = "/etc/telegraf/cert.pem" + # ssl_key = "/etc/telegraf/key.pem" + ## Use SSL but skip chain & host verification + # insecure_skip_verify = false + + ## HTTP response timeout (default: 5s) + response_timeout = "5s" ``` ### Measurements & Fields: diff --git a/plugins/inputs/nginx/nginx.go b/plugins/inputs/nginx/nginx.go index f439c1eeb..d389997e2 100644 --- a/plugins/inputs/nginx/nginx.go +++ b/plugins/inputs/nginx/nginx.go @@ -12,16 +12,39 @@ import ( "time" "github.com/influxdata/telegraf" + "github.com/influxdata/telegraf/internal" "github.com/influxdata/telegraf/plugins/inputs" ) type Nginx struct { + // List of status URLs Urls []string + // Path to CA file + SSLCA string `toml:"ssl_ca"` + // Path to client cert file + SSLCert string `toml:"ssl_cert"` + // Path to cert key file + SSLKey string `toml:"ssl_key"` + // Use SSL but skip chain & host verification + InsecureSkipVerify bool + // HTTP client + client *http.Client + // Response timeout + ResponseTimeout internal.Duration } var sampleConfig = ` - ## An array of Nginx stub_status URI to gather stats. - urls = ["http://localhost/status"] + # An array of Nginx stub_status URI to gather stats. + urls = ["http://localhost/server_status"] + + # TLS/SSL configuration + ssl_ca = "/etc/telegraf/ca.pem" + ssl_cert = "/etc/telegraf/cert.cer" + ssl_key = "/etc/telegraf/key.key" + insecure_skip_verify = false + + # HTTP response timeout (default: 5s) + response_timeout = "5s" ` func (n *Nginx) SampleConfig() string { @@ -35,6 +58,16 @@ func (n *Nginx) Description() string { func (n *Nginx) Gather(acc telegraf.Accumulator) error { var wg sync.WaitGroup + // Create an HTTP client that is re-used for each + // collection interval + if n.client == nil { + client, err := n.createHttpClient() + if err != nil { + return err + } + n.client = client + } + for _, u := range n.Urls { addr, err := url.Parse(u) if err != nil { @@ -52,17 +85,29 @@ func (n *Nginx) Gather(acc telegraf.Accumulator) error { return nil } -var tr = &http.Transport{ - ResponseHeaderTimeout: time.Duration(3 * time.Second), -} +func (n *Nginx) createHttpClient() (*http.Client, error) { + tlsCfg, err := internal.GetTLSConfig( + n.SSLCert, n.SSLKey, n.SSLCA, n.InsecureSkipVerify) + if err != nil { + return nil, err + } -var client = &http.Client{ - Transport: tr, - Timeout: time.Duration(4 * time.Second), + if n.ResponseTimeout.Duration < time.Second { + n.ResponseTimeout.Duration = time.Second * 5 + } + + client := &http.Client{ + Transport: &http.Transport{ + TLSClientConfig: tlsCfg, + }, + Timeout: n.ResponseTimeout.Duration, + } + + return client, nil } func (n *Nginx) gatherUrl(addr *url.URL, acc telegraf.Accumulator) error { - resp, err := client.Get(addr.String()) + resp, err := n.client.Get(addr.String()) if err != nil { return fmt.Errorf("error making HTTP request to %s: %s", addr.String(), err) }