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(inputs.firehose): Add new plugin #15988

Draft
wants to merge 3 commits into
base: master
Choose a base branch
from

Conversation

syedmhashim
Copy link

Summary

The firehose input plugin would be used to receive data from AWS Data Firehose.

Checklist

  • No AI generated code was used in this PR

Related issues

resolves #15870

@telegraf-tiger telegraf-tiger bot added the feat Improvement on an existing feature such as adding a new setting/mode to an existing plugin label Oct 7, 2024
@srebhan srebhan changed the title feat(inputs/firehose): add input plugin for AWS Data Firehose feat(inputs.firehose): Add new plugin Oct 8, 2024
@telegraf-tiger telegraf-tiger bot added the plugin/input 1. Request for new input plugins 2. Issues/PRs that are related to input plugins label Oct 8, 2024
Copy link
Member

@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.

@syedmhashim I do have some comments, mostly on style, so overall this looks quite promising. I urge you to keep the code as simple and less nested as possible to ease review and debugging. And of course some unit-tests would be great!

plugins/inputs/firehose/README.md Outdated Show resolved Hide resolved
plugins/inputs/firehose/README.md Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
@srebhan srebhan self-assigned this Oct 8, 2024
@syedmhashim
Copy link
Author

@syedmhashim I do have some comments, mostly on style, so overall this looks quite promising. I urge you to keep the code as simple and less nested as possible to ease review and debugging. And of course some unit-tests would be great!

Thanks for the review. Will definitely go over the comments and update accordingly. Just FYI, I have been using http_listener_v2 input plugin as a reference to write the code. The unit tests will come soon as well

@srebhan
Copy link
Member

srebhan commented Oct 9, 2024

Yeah we do have some older code we didn't adapt yet but things changed both on the golang side as well as on us being more strict with the way things are done. ;-) No worries, we will figure it out together. :-)

@srebhan
Copy link
Member

srebhan commented Oct 10, 2024

@syedmhashim I'm loosing a bit the track in the discussion above, could you please push an update with the stuff that is clear and then we discuss the unclear parts?

@syedmhashim
Copy link
Author

@srebhan Hey! Just pushed some changes and commented "done" on the threads that I resolved. Sorry for the delay. I got occupied with my job

Copy link
Member

@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.

That looks much better @syedmhashim! Some more cleanups and comments from my side...

plugins/inputs/firehose/README.md Outdated Show resolved Hide resolved
plugins/inputs/firehose/README.md Outdated Show resolved Hide resolved
plugins/inputs/firehose/README.md Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose_request.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose_request.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose_request.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose_request.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose_request.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose_request.go Outdated Show resolved Hide resolved
@syedmhashim
Copy link
Author

@srebhan Hi! Pushed some changes and added comments where relevant

Copy link
Member

@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.

@syedmhashim thanks for the update. I tried to put more concrete suggestions into my review. Overall, I think we are almost there, the only thing missing are unit-tests with a mocked sender...

plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose_request.go Show resolved Hide resolved
plugins/inputs/firehose/sample.conf Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose_request.go Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
Copy link
Member

@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.

Really nice @syedmhashim! Some very small things with the biggest being that log messages should start with a captial letter... The only thing missing are the unit-tests...

plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
plugins/inputs/firehose/firehose.go Outdated Show resolved Hide resolved
@syedmhashim
Copy link
Author

Hi @srebhan. In addition to the changes that you suggested, I also made some changes to the code(see last commit) that I think would make it more clean and readable. P.S I think it also helps to achieve separation of concern since now all processing of the request is handled by firehose_request.go while firehose.go mostly focus on adding metrics:

Changes to :

  • firehose_request.go
    • Added newRequest method to handle the creation of request object and (gzip +) json decoding of the request body
    • Added processRequest method to handle the authentication, validation, base64 decoding and parameter extraction
    • I’ve tried to set the response status code mostly in firehose_request.go
  • firehose.go
    • Added handleRequest method. This helps to get rid of the redundant sendResponse code block.

I'd like to hear your thoughts on this

@syedmhashim syedmhashim force-pushed the master branch 2 times, most recently from 0138d46 to 9d69797 Compare December 5, 2024 07:13
Copy link
Member

@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.

@syedmhashim thanks for the update. I do have some smaller comments in the code but nothing big.

Regarding the tests, I suggest that you don't test the request separately but simply use a http client and send data to the plugin. You might also want to implement a general test-case setup similar to what we do in socket listener tests...

If you need help with the tests, please provide some payload examples and invite me to your branch and I'll help you to drive this PR over the finish line...

"github.com/influxdata/telegraf"
"github.com/influxdata/telegraf/config"
"github.com/influxdata/telegraf/internal"
tlsint "github.com/influxdata/telegraf/plugins/common/tls"
Copy link
Member

Choose a reason for hiding this comment

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

We no do have an unwritten convention to use

Suggested change
tlsint "github.com/influxdata/telegraf/plugins/common/tls"
common_tls "github.com/influxdata/telegraf/plugins/common/tls"

i.e. prefix packages in plugins/common with common_...

Copy link
Author

Choose a reason for hiding this comment

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

updated

f.listener, err = net.Listen("tcp", f.ServiceAddress)
}
if err != nil {
return err
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
return err
return fmt.Errorf("creating listener failed: %w", err)

Copy link
Author

Choose a reason for hiding this comment

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

updated

go func() {
if err := f.server.Serve(f.listener); err != nil {
if !errors.Is(err, net.ErrClosed) {
f.Log.Errorf("Starting server failed: %v", err)
Copy link
Member

Choose a reason for hiding this comment

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

I think this is not only on startup but might also return errors later... So how about

Suggested change
f.Log.Errorf("Starting server failed: %v", err)
f.Log.Errorf("Server failed: %v", err)

Copy link
Author

Choose a reason for hiding this comment

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

Updated

Comment on lines 109 to 110
err := f.server.Shutdown(context.Background())
if err != nil {
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
err := f.server.Shutdown(context.Background())
if err != nil {
if err := f.server.Shutdown(context.Background()); err != nil {

Copy link
Author

Choose a reason for hiding this comment

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

updated

Comment on lines 128 to 131
func (f *Firehose) handleRequest(req *http.Request) (r *request) {
var err error
if r, err = newRequest(req); err != nil {
f.Log.Errorf("Creating request object failed: %v", err)
return r
}
Copy link
Member

Choose a reason for hiding this comment

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

How about returning the actual error here and do the logging in ServeHTTP? This will save a few lines I think

Suggested change
func (f *Firehose) handleRequest(req *http.Request) (r *request) {
var err error
if r, err = newRequest(req); err != nil {
f.Log.Errorf("Creating request object failed: %v", err)
return r
}
func (f *Firehose) handleRequest(req *http.Request) (*request, error) {
r, err := newRequest(req)
if err != nil {
return fmt.Errorf("creating request failed: %w", err)
}

of course you need to modify the code below and in ServeHTTP...

Copy link
Author

Choose a reason for hiding this comment

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

I tried implementing this but doesn’t help. The line count remains the same as we need to introduce err checking in the ServeHTTP function. I made some other changes which saves us a couple lines though

@syedmhashim
Copy link
Author

@srebhan Hey. Just sent you an invite! The payload needs to be in the following format with data having the actual b64 encoded text that would be parsed (based on the parser set) after decoding:

{
    "requestId": “test-id",
    "timestamp": 123456789,
    "records": [
        {
          "data": "aGVsbG8gd29ybGQK" // "hello world"
        }
    ]
}

@telegraf-tiger
Copy link
Contributor

telegraf-tiger bot commented Dec 5, 2024

Download PR build artifacts for linux_amd64.tar.gz, darwin_arm64.tar.gz, and windows_amd64.zip.
Downloads for additional architectures and packages are available below.

⚠️ This pull request increases the Telegraf binary size by 1.78 % for linux amd64 (new size: 261.3 MB, nightly size 256.7 MB)

📦 Click here to get additional PR build artifacts

Artifact URLs

DEB RPM TAR GZ ZIP
amd64.deb aarch64.rpm darwin_amd64.tar.gz windows_amd64.zip
arm64.deb armel.rpm darwin_arm64.tar.gz windows_arm64.zip
armel.deb armv6hl.rpm freebsd_amd64.tar.gz windows_i386.zip
armhf.deb i386.rpm freebsd_armv7.tar.gz
i386.deb ppc64le.rpm freebsd_i386.tar.gz
mips.deb riscv64.rpm linux_amd64.tar.gz
mipsel.deb s390x.rpm linux_arm64.tar.gz
ppc64el.deb x86_64.rpm linux_armel.tar.gz
riscv64.deb linux_armhf.tar.gz
s390x.deb linux_i386.tar.gz
linux_mips.tar.gz
linux_mipsel.tar.gz
linux_ppc64le.tar.gz
linux_riscv64.tar.gz
linux_s390x.tar.gz

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 plugin/input 1. Request for new input plugins 2. Issues/PRs that are related to input plugins
Projects
None yet
Development

Successfully merging this pull request may close these issues.

AWS Data Firehose HTTP Endpoint Input Plugin
2 participants