From 837d62d72b8891f1dcebeab8e0e087457b9838a7 Mon Sep 17 00:00:00 2001 From: Spyros Psarras Date: Tue, 4 Jul 2023 15:59:21 +0200 Subject: [PATCH 1/3] Allow more headers to be added from console --- .gitignore | 1 + README.md | 2 ++ cmd/cspr-collector/main.go | 11 +++++++++-- output_http.go | 24 +++++++++++++++++++++++- 4 files changed, 35 insertions(+), 3 deletions(-) diff --git a/.gitignore b/.gitignore index c086591..15f10d0 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1,3 @@ /.idea/ /build/ +.vscode diff --git a/README.md b/README.md index 1c640eb..40d46ce 100644 --- a/README.md +++ b/README.md @@ -27,6 +27,8 @@ Usage of ./build/cspr-collector: enable http output -output-http-host string http host to send the csp violations to (default "http://localhost:80/") + -output-http-headers string + header header key with value to send with the http request. Example "Authorization: ApiKey " -output-stdout enable stdout output ``` diff --git a/cmd/cspr-collector/main.go b/cmd/cspr-collector/main.go index be05e78..337af52 100644 --- a/cmd/cspr-collector/main.go +++ b/cmd/cspr-collector/main.go @@ -3,11 +3,12 @@ package main import ( "context" "flag" - cspr "github.com/mhilker/cspr-collector" "log" "net/http" "os" "os/signal" + + cspr "github.com/mhilker/cspr-collector" ) var ( @@ -16,6 +17,7 @@ var ( OutputStdout = flag.Bool("output-stdout", false, "enable stdout output") OutputHTTPEnabled = flag.Bool("output-http", false, "enable http output") OutputHTTPHost = flag.String("output-http-host", "http://localhost:80/", "http host to send the csp violations to") + OutputHTTPHeaders = flag.String("output-http-headers", "", "additional headers for HTTP output") OutputESEnabled = flag.Bool("output-es", false, "enable elasticsearch output") OutputESHost = flag.String("output-es-host", "http://localhost:9200/", "elasticsearch host to send the csp violations to") OutputESIndex = flag.String("output-es-index", "cspr-violations", "elasticsearch index to save the csp violations in") @@ -67,7 +69,12 @@ func NewOutput() *cspr.CombinedOutput { if *OutputHTTPEnabled { log.Printf("Enable HTTP Output.") - outputs = append(outputs, &cspr.HTTPOutput{Url: *OutputHTTPHost}) + headers := cspr.ParseHeaders(*OutputHTTPHeaders) + + outputs = append(outputs, &cspr.HTTPOutput{ + Url: *OutputHTTPHost, + Headers: headers, + }) } if *OutputESEnabled { diff --git a/output_http.go b/output_http.go index b3ae95b..f42a06b 100644 --- a/output_http.go +++ b/output_http.go @@ -5,10 +5,12 @@ import ( "encoding/json" "log" "net/http" + "strings" ) type HTTPOutput struct { - Url string + Url string + Headers map[string]string } func (o *HTTPOutput) Write(data []CSPRequest) { @@ -24,6 +26,10 @@ func (o *HTTPOutput) Write(data []CSPRequest) { log.Print(err.Error()) return } + + for key, value := range o.Headers { + request.Header.Set(key, value) + } request.Header.Set("Content-Type", "application/json") client := &http.Client{} @@ -37,3 +43,19 @@ func (o *HTTPOutput) Write(data []CSPRequest) { log.Print("Response Status:", response.Status) } } + +func ParseHeaders(headerString string) map[string]string { + headers := make(map[string]string) + pairs := strings.Split(headerString, ",") + + for _, pair := range pairs { + split := strings.SplitN(pair, ":", 2) + if len(split) == 2 { + key := strings.TrimSpace(split[0]) + value := strings.TrimSpace(split[1]) + headers[key] = value + } + } + + return headers +} From ad86757c8603581233296d463febd093638ef00d Mon Sep 17 00:00:00 2001 From: Spyros Psarras Date: Wed, 16 Aug 2023 10:10:47 +0200 Subject: [PATCH 2/3] add info on README.ms --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 40d46ce..9900cf8 100644 --- a/README.md +++ b/README.md @@ -27,6 +27,8 @@ Usage of ./build/cspr-collector: enable http output -output-http-host string http host to send the csp violations to (default "http://localhost:80/") + -output-http-headers string + additional headers for HTTP output -output-http-headers string header header key with value to send with the http request. Example "Authorization: ApiKey " -output-stdout From 39e2d3a5ea6eec639ef2847d3bbdf0c2910eb9cf Mon Sep 17 00:00:00 2001 From: Spyros Psarras Date: Wed, 16 Aug 2023 10:49:57 +0200 Subject: [PATCH 3/3] add /health endpoint --- README.md | 8 ++++++-- collector.go | 11 ++++++++++- dispatcher.go | 25 +++++++++++++++---------- 3 files changed, 31 insertions(+), 13 deletions(-) diff --git a/README.md b/README.md index 9900cf8..b044291 100644 --- a/README.md +++ b/README.md @@ -27,8 +27,6 @@ Usage of ./build/cspr-collector: enable http output -output-http-host string http host to send the csp violations to (default "http://localhost:80/") - -output-http-headers string - additional headers for HTTP output -output-http-headers string header header key with value to send with the http request. Example "Authorization: ApiKey " -output-stdout @@ -102,6 +100,12 @@ curl -X POST \ go fmt ./... ``` +## Health check endpoint +endpoint with health response "OK" +```bash +curl http://localhost:8080/health +``` + ## License The MIT License (MIT). Please see the [license file](LICENSE.md) for more information. diff --git a/collector.go b/collector.go index a4047ed..517badb 100644 --- a/collector.go +++ b/collector.go @@ -19,6 +19,11 @@ type Collector struct { } func (c *Collector) ServeHTTP(w http.ResponseWriter, r *http.Request) { + if r.RequestURI == "/health" { + c.handleHealth(w) + return + } + if r.RequestURI != "/" { message := fmt.Sprintf("Path \"%s\" not found.", r.RequestURI) c.response(w, http.StatusNotFound, message) @@ -58,7 +63,6 @@ func (c *Collector) ServeHTTP(w http.ResponseWriter, r *http.Request) { c.WorkQueue <- data c.response(w, http.StatusCreated, "") - return } func (c *Collector) response(w http.ResponseWriter, status int, message string) { @@ -82,3 +86,8 @@ func (c *Collector) response(w http.ResponseWriter, status int, message string) log.Fatal(err) } } + +func (c *Collector) handleHealth(w http.ResponseWriter) { + w.WriteHeader(http.StatusOK) + w.Write([]byte("OK")) +} diff --git a/dispatcher.go b/dispatcher.go index acf83bd..b187381 100644 --- a/dispatcher.go +++ b/dispatcher.go @@ -31,15 +31,20 @@ func (d *Dispatcher) Run() { } func (d *Dispatcher) start() { - for { - select { - case work := <-d.WorkQueue: - log.Print("Received work request.") - go func() { - worker := <-d.WorkerQueue - log.Print("Dispatching work request.") - worker <- work - }() - } + for work := range d.WorkQueue { + log.Print("Received work request.") + go func(w interface{}) { + worker := <-d.WorkerQueue + log.Print("Dispatching work request.") + + // Perform a type assertion + typedWork, ok := w.(CSPRequest) + if !ok { + log.Print("Invalid work request type") + return + } + + worker <- typedWork + }(work) } }