Skip to content

Commit

Permalink
Add support for field/tag keys to strings processor (influxdata#6129)
Browse files Browse the repository at this point in the history
  • Loading branch information
glinton authored and bitcharmer committed Oct 18, 2019
1 parent 5664537 commit a9a4bdd
Show file tree
Hide file tree
Showing 3 changed files with 411 additions and 10 deletions.
52 changes: 42 additions & 10 deletions plugins/processors/strings/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,41 +14,50 @@ Implemented functions are:

Please note that in this implementation these are processed in the order that they appear above.

Specify the `measurement`, `tag` or `field` that you want processed in each section and optionally a `dest` if you want the result stored in a new tag or field. You can specify lots of transformations on data with a single strings processor.
Specify the `measurement`, `tag`, `tag_key`, `field`, or `field_key` that you want processed in each section and optionally a `dest` if you want the result stored in a new tag or field. You can specify lots of transformations on data with a single strings processor.

If you'd like to apply the change to every `tag`, `field`, or `measurement`, use the value "*" for each respective field. Note that the `dest` field will be ignored if "*" is used
If you'd like to apply the change to every `tag`, `tag_key`, `field`, `field_key`, or `measurement`, use the value `"*"` for each respective field. Note that the `dest` field will be ignored if `"*"` is used.

If you'd like to apply multiple processings to the same `tag_key` or `field_key`, note the process order stated above. See [Example 2]() for an example.

### Configuration:

```toml
[[processors.strings]]
# [[processors.strings.uppercase]]
# tag = "method"

## Convert a field value to lowercase and store in a new field
# [[processors.strings.lowercase]]
# field = "uri_stem"
# dest = "uri_stem_normalised"

## Convert a tag value to lowercase
## Convert a tag value to uppercase
# [[processors.strings.uppercase]]
# tag = "method"

## Trim leading and trailing whitespace using the default cutset
# [[processors.strings.trim]]
# field = "message"

## Trim leading characters in cutset
# [[processors.strings.trim_left]]
# field = "message"
# cutset = "\t"

## Trim trailing characters in cutset
# [[processors.strings.trim_right]]
# field = "message"
# cutset = "\r\n"

## Trim the given prefix from the field
# [[processors.strings.trim_prefix]]
# field = "my_value"
# prefix = "my_"

## Trim the given suffix from the field
# [[processors.strings.trim_suffix]]
# field = "read_count"
# suffix = "_count"

## Replace all non-overlapping instances of old with new
# [[processors.strings.replace]]
# measurement = "*"
# old = ":"
Expand Down Expand Up @@ -79,10 +88,10 @@ the operation and keep the old name.
```toml
[[processors.strings]]
[[processors.strings.lowercase]]
field = "uri-stem"
tag = "uri_stem"

[[processors.strings.trim_prefix]]
field = "uri_stem"
tag = "uri_stem"
prefix = "/api/"

[[processors.strings.uppercase]]
Expand All @@ -92,10 +101,33 @@ the operation and keep the old name.

**Input**
```
iis_log,method=get,uri_stem=/API/HealthCheck cs-host="MIXEDCASE_host",referrer="-",ident="-",http_version=1.1,agent="UserAgent",resp_bytes=270i 1519652321000000000
iis_log,method=get,uri_stem=/API/HealthCheck cs-host="MIXEDCASE_host",http_version=1.1 1519652321000000000
```

**Output**
```
iis_log,method=get,uri_stem=healthcheck cs-host="MIXEDCASE_host",http_version=1.1,cs-host_normalised="MIXEDCASE_HOST" 1519652321000000000
```

### Example 2
**Config**
```toml
[[processors.strings]]
[[processors.strings.lowercase]]
tag_key = "URI-Stem"

[[processors.strings.replace]]
tag_key = "uri-stem"
old = "-"
new = "_"
```

**Input**
```
iis_log,URI-Stem=/API/HealthCheck http_version=1.1 1519652321000000000
```

**Output**
```
iis_log,method=get,uri_stem=healthcheck cs-host="MIXEDCASE_host",cs-host_normalised="MIXEDCASE_HOST",referrer="-",ident="-",http_version=1.1,agent="UserAgent",resp_bytes=270i 1519652321000000000
iis_log,uri_stem=/API/HealthCheck http_version=1.1 1519652321000000000
```
52 changes: 52 additions & 0 deletions plugins/processors/strings/strings.go
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,9 @@ type ConvertFunc func(s string) string

type converter struct {
Field string
FieldKey string
Tag string
TagKey string
Measurement string
Dest string
Cutset string
Expand Down Expand Up @@ -109,6 +111,27 @@ func (c *converter) convertTag(metric telegraf.Metric) {
}
}

func (c *converter) convertTagKey(metric telegraf.Metric) {
var tags map[string]string
if c.TagKey == "*" {
tags = metric.Tags()
} else {
tags = make(map[string]string)
tv, ok := metric.GetTag(c.TagKey)
if !ok {
return
}
tags[c.TagKey] = tv
}

for key, value := range tags {
if k := c.fn(key); k != "" {
metric.RemoveTag(key)
metric.AddTag(k, value)
}
}
}

func (c *converter) convertField(metric telegraf.Metric) {
var fields map[string]interface{}
if c.Field == "*" {
Expand All @@ -133,6 +156,27 @@ func (c *converter) convertField(metric telegraf.Metric) {
}
}

func (c *converter) convertFieldKey(metric telegraf.Metric) {
var fields map[string]interface{}
if c.FieldKey == "*" {
fields = metric.Fields()
} else {
fields = make(map[string]interface{})
fv, ok := metric.GetField(c.FieldKey)
if !ok {
return
}
fields[c.FieldKey] = fv
}

for key, value := range fields {
if k := c.fn(key); k != "" {
metric.RemoveField(key)
metric.AddField(k, value)
}
}
}

func (c *converter) convertMeasurement(metric telegraf.Metric) {
if metric.Name() != c.Measurement && c.Measurement != "*" {
return
Expand All @@ -146,10 +190,18 @@ func (c *converter) convert(metric telegraf.Metric) {
c.convertField(metric)
}

if c.FieldKey != "" {
c.convertFieldKey(metric)
}

if c.Tag != "" {
c.convertTag(metric)
}

if c.TagKey != "" {
c.convertTagKey(metric)
}

if c.Measurement != "" {
c.convertMeasurement(metric)
}
Expand Down
Loading

0 comments on commit a9a4bdd

Please sign in to comment.