Add support for ${} env vars in configuration file (#5648)

This commit is contained in:
Daniel Nelson 2019-03-29 16:02:10 -07:00 committed by GitHub
parent aac013f8ab
commit 6feb6c1853
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 30 additions and 18 deletions

View File

@ -34,10 +34,10 @@ configuration files.
### Environment Variables ### Environment Variables
Environment variables can be used anywhere in the config file, simply prepend Environment variables can be used anywhere in the config file, simply surround
them with `$`. Replacement occurs before file parsing. For strings them with `${}`. Replacement occurs before file parsing. For strings
the variable must be within quotes, e.g., `"$STR_VAR"`, for numbers and booleans the variable must be within quotes, e.g., `"${STR_VAR}"`, for numbers and booleans
they should be unquoted, e.g., `$INT_VAR`, `$BOOL_VAR`. they should be unquoted, e.g., `${INT_VAR}`, `${BOOL_VAR}`.
When using the `.deb` or `.rpm` packages, you can define environment variables When using the `.deb` or `.rpm` packages, you can define environment variables
in the `/etc/default/telegraf` file. in the `/etc/default/telegraf` file.
@ -55,14 +55,14 @@ INFLUX_PASSWORD="monkey123"
`/etc/telegraf.conf`: `/etc/telegraf.conf`:
```toml ```toml
[global_tags] [global_tags]
user = "$USER" user = "${USER}"
[[inputs.mem]] [[inputs.mem]]
[[outputs.influxdb]] [[outputs.influxdb]]
urls = ["$INFLUX_URL"] urls = ["${INFLUX_URL}"]
skip_database_creation = $INFLUX_SKIP_DATABASE_CREATION skip_database_creation = ${INFLUX_SKIP_DATABASE_CREATION}
password = "$INFLUX_PASSWORD" password = "${INFLUX_PASSWORD}"
``` ```
The above files will produce the following effective configuration file to be The above files will produce the following effective configuration file to be

View File

@ -40,7 +40,7 @@ var (
outputDefaults = []string{"influxdb"} outputDefaults = []string{"influxdb"}
// envVarRe is a regex to find environment variables in the config file // envVarRe is a regex to find environment variables in the config file
envVarRe = regexp.MustCompile(`\$\w+`) envVarRe = regexp.MustCompile(`\$\{(\w+)\}|\$(\w+)`)
envVarEscaper = strings.NewReplacer( envVarEscaper = strings.NewReplacer(
`"`, `\"`, `"`, `\"`,
@ -208,9 +208,9 @@ var header = `# Telegraf Configuration
# Use 'telegraf -config telegraf.conf -test' to see what metrics a config # Use 'telegraf -config telegraf.conf -test' to see what metrics a config
# file would generate. # file would generate.
# #
# Environment variables can be used anywhere in this config file, simply prepend # Environment variables can be used anywhere in this config file, simply surround
# them with $. For strings the variable must be within quotes (ie, "$STR_VAR"), # them with ${}. For strings the variable must be within quotes (ie, "${STR_VAR}"),
# for numbers and booleans they should be plain (ie, $INT_VAR, $BOOL_VAR) # for numbers and booleans they should be plain (ie, ${INT_VAR}, ${BOOL_VAR})
# Global tags can be specified here in key="value" format. # Global tags can be specified here in key="value" format.
@ -787,12 +787,25 @@ func fetchConfig(u *url.URL) ([]byte, error) {
func parseConfig(contents []byte) (*ast.Table, error) { func parseConfig(contents []byte) (*ast.Table, error) {
contents = trimBOM(contents) contents = trimBOM(contents)
env_vars := envVarRe.FindAll(contents, -1) parameters := envVarRe.FindAllSubmatch(contents, -1)
for _, env_var := range env_vars { for _, parameter := range parameters {
if len(parameter) != 3 {
continue
}
var env_var []byte
if parameter[1] != nil {
env_var = parameter[1]
} else if parameter[2] != nil {
env_var = parameter[2]
} else {
continue
}
env_val, ok := os.LookupEnv(strings.TrimPrefix(string(env_var), "$")) env_val, ok := os.LookupEnv(strings.TrimPrefix(string(env_var), "$"))
if ok { if ok {
env_val = escapeEnv(env_val) env_val = escapeEnv(env_val)
contents = bytes.Replace(contents, env_var, []byte(env_val), 1) contents = bytes.Replace(contents, parameter[0], []byte(env_val), 1)
} }
} }

View File

@ -11,7 +11,6 @@ import (
"github.com/influxdata/telegraf/plugins/inputs/memcached" "github.com/influxdata/telegraf/plugins/inputs/memcached"
"github.com/influxdata/telegraf/plugins/inputs/procstat" "github.com/influxdata/telegraf/plugins/inputs/procstat"
"github.com/influxdata/telegraf/plugins/parsers" "github.com/influxdata/telegraf/plugins/parsers"
"github.com/stretchr/testify/assert" "github.com/stretchr/testify/assert"
) )
@ -28,7 +27,7 @@ func TestConfig_LoadSingleInputWithEnvVars(t *testing.T) {
filter := models.Filter{ filter := models.Filter{
NameDrop: []string{"metricname2"}, NameDrop: []string{"metricname2"},
NamePass: []string{"metricname1"}, NamePass: []string{"metricname1", "ip_192.168.1.1_name"},
FieldDrop: []string{"other", "stuff"}, FieldDrop: []string{"other", "stuff"},
FieldPass: []string{"some", "strings"}, FieldPass: []string{"some", "strings"},
TagDrop: []models.TagFilter{ TagDrop: []models.TagFilter{

View File

@ -1,6 +1,6 @@
[[inputs.memcached]] [[inputs.memcached]]
servers = ["$MY_TEST_SERVER"] servers = ["$MY_TEST_SERVER"]
namepass = ["metricname1"] namepass = ["metricname1", "ip_${MY_TEST_SERVER}_name"]
namedrop = ["metricname2"] namedrop = ["metricname2"]
fieldpass = ["some", "strings"] fieldpass = ["some", "strings"]
fielddrop = ["other", "stuff"] fielddrop = ["other", "stuff"]