diff --git a/config/config.go b/config/config.go index 4121c7168..3a417427e 100644 --- a/config/config.go +++ b/config/config.go @@ -1590,6 +1590,7 @@ func (c *Config) buildSerializer(tbl *ast.Table) (serializers.Serializer, error) c.getFieldStringSlice(tbl, "wavefront_source_override", &sc.WavefrontSourceOverride) c.getFieldBool(tbl, "wavefront_use_strict", &sc.WavefrontUseStrict) + c.getFieldBool(tbl, "wavefront_disable_prefix_conversion", &sc.WavefrontDisablePrefixConversion) c.getFieldBool(tbl, "prometheus_export_timestamp", &sc.PrometheusExportTimestamp) c.getFieldBool(tbl, "prometheus_sort_metrics", &sc.PrometheusSortMetrics) diff --git a/plugins/serializers/registry.go b/plugins/serializers/registry.go index 144be0c37..5030531bf 100644 --- a/plugins/serializers/registry.go +++ b/plugins/serializers/registry.go @@ -104,6 +104,9 @@ type Config struct { // When enabled forward slash (/) and comma (,) will be accepted WavefrontUseStrict bool `toml:"wavefront_use_strict"` + // Convert "_" in prefixes to "." for Wavefront + WavefrontDisablePrefixConversion bool `toml:"wavefront_disable_prefix_conversion"` + // Include the metric timestamp on each sample. PrometheusExportTimestamp bool `toml:"prometheus_export_timestamp"` @@ -134,7 +137,7 @@ func NewSerializer(config *Config) (Serializer, error) { case "carbon2": serializer, err = NewCarbon2Serializer(config.Carbon2Format, config.Carbon2SanitizeReplaceChar) case "wavefront": - serializer, err = NewWavefrontSerializer(config.Prefix, config.WavefrontUseStrict, config.WavefrontSourceOverride) + serializer, err = NewWavefrontSerializer(config.Prefix, config.WavefrontUseStrict, config.WavefrontSourceOverride, config.WavefrontDisablePrefixConversion) case "prometheus": serializer, err = NewPrometheusSerializer(config) case "prometheusremotewrite": @@ -187,8 +190,8 @@ func NewPrometheusSerializer(config *Config) (Serializer, error) { }) } -func NewWavefrontSerializer(prefix string, useStrict bool, sourceOverride []string) (Serializer, error) { - return wavefront.NewSerializer(prefix, useStrict, sourceOverride) +func NewWavefrontSerializer(prefix string, useStrict bool, sourceOverride []string, disablePrefixConversions bool) (Serializer, error) { + return wavefront.NewSerializer(prefix, useStrict, sourceOverride, disablePrefixConversions) } func NewJSONSerializer(timestampUnits time.Duration, timestampFormat string) (Serializer, error) { diff --git a/plugins/serializers/wavefront/README.md b/plugins/serializers/wavefront/README.md index 3ab0fa397..7495f9f4d 100644 --- a/plugins/serializers/wavefront/README.md +++ b/plugins/serializers/wavefront/README.md @@ -20,6 +20,10 @@ The `wavefront` serializer translates the Telegraf metric format to the [Wavefro ## more about them here: ## https://github.com/influxdata/telegraf/blob/master/docs/DATA_FORMATS_OUTPUT.md data_format = "wavefront" + ## Users who wish their prefix paths to not be converted may set the following: + ## default behavior (enabled prefix/path conversion): prod.prefix.name.metric.name + ## configurable behavior (disabled prefix/path conversion): prod.prefix_name.metric_name + # wavefront_disable_prefix_conversion = true ``` ## Metrics diff --git a/plugins/serializers/wavefront/wavefront.go b/plugins/serializers/wavefront/wavefront.go index 2bb01266e..a05b0becd 100755 --- a/plugins/serializers/wavefront/wavefront.go +++ b/plugins/serializers/wavefront/wavefront.go @@ -12,11 +12,12 @@ import ( // WavefrontSerializer : WavefrontSerializer struct type WavefrontSerializer struct { - Prefix string - UseStrict bool - SourceOverride []string - scratch buffer - mu sync.Mutex // buffer mutex + Prefix string + UseStrict bool + SourceOverride []string + DisablePrefixConversions bool + scratch buffer + mu sync.Mutex // buffer mutex } // catch many of the invalid chars that could appear in a metric or tag name @@ -40,11 +41,12 @@ var tagValueReplacer = strings.NewReplacer("\"", "\\\"", "*", "-") var pathReplacer = strings.NewReplacer("_", ".") -func NewSerializer(prefix string, useStrict bool, sourceOverride []string) (*WavefrontSerializer, error) { +func NewSerializer(prefix string, useStrict bool, sourceOverride []string, disablePrefixConversion bool) (*WavefrontSerializer, error) { s := &WavefrontSerializer{ - Prefix: prefix, - UseStrict: useStrict, - SourceOverride: sourceOverride, + Prefix: prefix, + UseStrict: useStrict, + SourceOverride: sourceOverride, + DisablePrefixConversions: disablePrefixConversion, } return s, nil } @@ -67,7 +69,9 @@ func (s *WavefrontSerializer) serializeMetric(m telegraf.Metric) { name = sanitizedChars.Replace(name) } - name = pathReplacer.Replace(name) + if !s.DisablePrefixConversions { + name = pathReplacer.Replace(name) + } metricValue, valid := buildValue(value, name) if !valid {