Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(serializers): Add a serializer based on go templates #13656

Merged
merged 16 commits into from
Jul 28, 2023

Conversation

gazpachoking
Copy link
Contributor

Required for all PRs

resolves #13637

Adds a new serializer that lets the user define a go template for the serialization format.

I haven't really used Go before, so this might need a bit of review.

@gazpachoking
Copy link
Contributor Author

Hmmm. I was very cut and pasty with this PR. Now reading #13606, I'm thinking I shouldn't fully copy the way it's being done in the template processor plugin, as it looks like we are moving away from that method.

@srebhan
Copy link
Contributor

srebhan commented Jul 24, 2023

Hmmm. I was very cut and pasty with this PR. Now reading #13606, I'm thinking I shouldn't fully copy the way it's being done in the template processor plugin, as it looks like we are moving away from that method.

@gazpachoking right. You can just use the metric directly and the TemplateMetric interface. You might want to take a look at the lookup processor...

@srebhan srebhan added feat Improvement on an existing feature such as adding a new setting/mode to an existing plugin plugin/serializer labels Jul 24, 2023
Copy link
Contributor

@srebhan srebhan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@gazpachoking this already looks very beautiful, thanks for your contribution. I do have some smaller comments and one request. The request is regarding the single vs. batch serialization. I think you should match the template input to what is intended by the user as the user cannot know which method is called.

plugins/serializers/template/template.go Outdated Show resolved Hide resolved
plugins/serializers/template/README.md Outdated Show resolved Hide resolved
plugins/serializers/template/template_test.go Outdated Show resolved Hide resolved
plugins/serializers/template/template_test.go Outdated Show resolved Hide resolved
@srebhan srebhan self-assigned this Jul 24, 2023
@gazpachoking
Copy link
Contributor Author

I don't believe the latest ci failure is to do with my changes.

@gazpachoking
Copy link
Contributor Author

gazpachoking commented Jul 24, 2023

Hmm, working with the go templating engine a bit has shown that it's a bit inflexible (without some helpers.) I'm thinking we should include the sprig functions here. Thoughts?

@powersj
Copy link
Contributor

powersj commented Jul 26, 2023

Hmm, working with the go templating engine a bit has shown that it's a bit inflexible (without some helpers.) I'm thinking we should include the sprig functions here. Thoughts?

Hmm sprig doesn't appear to be maintained or updated in ~year. Is there a use-case that you could provide for using them versus not using the library?

@powersj powersj added the waiting for response waiting for response from contributor label Jul 26, 2023
@gazpachoking
Copy link
Contributor Author

Hmm sprig doesn't appear to be maintained or updated in ~year. Is there a use-case that you could provide for using them versus not using the library?

I was having trouble trying to comma separate tags or metrics without putting a trailing comma. Really it's sorta convoluted even with sprig with tags, since their dict functions don't work directly on the tags map (they work fine on the fields map though.) Here's what I did using sprig, I couldn't even figure out how to do it at all without it.

template = "{{$tags := .Tags|toJson|fromJson}}{{range $tags|keys|initial}}{{.}}={{get $tags .}}, {{end}}{{$tags|keys|last}}={{$tags|values|last}}\n"

The toJson fromJson dance is the convoluted bit I mentioned. That converts the tag map from map[string]string to map[string]interface{} which is what's needed to use the sprig dict helpers.

I picked it because Helm uses it, and it's already used in the postgresql output plugin. I'm fine with removing it though, but I would like to figure out if doing commas between things is possible, as that seems like it might be a common use case.

@telegraf-tiger telegraf-tiger bot removed the waiting for response waiting for response from contributor label Jul 26, 2023
Copy link
Contributor

@srebhan srebhan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice update @gazpachoking! Have some more comments...

go.mod Outdated Show resolved Hide resolved
plugins/serializers/template/template.go Outdated Show resolved Hide resolved
plugins/serializers/template/template.go Outdated Show resolved Hide resolved
plugins/serializers/template/template.go Outdated Show resolved Hide resolved
Copy link
Contributor

@srebhan srebhan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I love the PR. @gazpachoking can you please show one config in the README where all available options are included to give users an overview of what is there!? You might then show more config-examples below for different use-cases....

plugins/serializers/template/README.md Show resolved Hide resolved
@gazpachoking
Copy link
Contributor Author

Added the batch_template option in the example. Also noticed that the TOML parser doesn't allow embedding double quotes inside a basic multi-line string, which the spec says should be fine. (it also doesn't seem to like single quotes within a multi-line literal string)

Copy link
Contributor

@srebhan srebhan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good to me. Thanks @gazpachoking for the cool serializer!

@srebhan srebhan changed the title feat(serializer.template): Add a serializer based on go templates feat(serializers): Add a serializer based on go templates Jul 28, 2023
@srebhan srebhan added the ready for final review This pull request has been reviewed and/or tested by multiple users and is ready for a final review. label Jul 28, 2023
@srebhan srebhan assigned powersj and unassigned srebhan Jul 28, 2023
@telegraf-tiger
Copy link
Contributor

@powersj powersj merged commit 283af2b into influxdata:master Jul 28, 2023
26 checks passed
@github-actions github-actions bot added this to the v1.28.0 milestone Jul 28, 2023
@ven0hm
Copy link

ven0hm commented Aug 3, 2023

Thank you @gazpachoking! This serializer is exactly what I need!

When I try to use it with [[outputs.file]] it works just fine.
But when I try the same with [[outputs.socket_writer]], it throws an error
plugin outputs.socket_writer: line 48: configuration specified the fields ["use_batch_format"], but they weren't used

Full config:

[[outputs.socket_writer]]
  address = "tcp://localhost:80"
  keep_alive_period = "10m"
  content_encoding = "identity"
  data_format = "template"
  use_batch_format = true
  batch_template = '''
{{range $metric := . -}}
{{range $metric.Fields | keys | initial -}}
{{.}}={{get $metric.Fields .}}, {{end}}
{{- $metric.Tag "name"}}={{$metric.Fields|values|last}}
{{end -}}
'''

I'm using telegraf-1.28.0~ff54c603_linux_amd64.tar.gz from the link above.
Should I submit this as a bug, or I'm just configuring it wrong?

@powersj
Copy link
Contributor

powersj commented Aug 3, 2023

["use_batch_format"], but they weren't used

This is not a valid option for the socket_writer. The socket writer writes each metric as it comes, not in batches.

@gazpachoking
Copy link
Contributor Author

@ven0hm Do you need the batch format for your purposes, or are individual metrics fine? Allowing batch format in the socket_writer plugin would be a valid feature request.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
feat Improvement on an existing feature such as adding a new setting/mode to an existing plugin new plugin plugin/serializer ready for final review This pull request has been reviewed and/or tested by multiple users and is ready for a final review.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Templatable output data_format
4 participants