summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFrancis Lavoie <lavofr@gmail.com>2023-03-27 18:40:15 -0400
committerGitHub <noreply@github.com>2023-03-27 22:40:15 +0000
commit2b3046de36bad70bd7e48478c99a8a030fb35b98 (patch)
treee9052b2c53ecfcffa0530248bc4337f33d6bfea5
parent1aef807c71b1ea8e70e664765e0010734aee468c (diff)
caddyhttp: Log request body bytes read (#5461)
-rw-r--r--modules/caddyhttp/server.go32
1 files changed, 32 insertions, 0 deletions
diff --git a/modules/caddyhttp/server.go b/modules/caddyhttp/server.go
index eb61806..82fdbe5 100644
--- a/modules/caddyhttp/server.go
+++ b/modules/caddyhttp/server.go
@@ -19,6 +19,7 @@ import (
"crypto/tls"
"encoding/json"
"fmt"
+ "io"
"net"
"net/http"
"net/netip"
@@ -259,6 +260,14 @@ func (s *Server) ServeHTTP(w http.ResponseWriter, r *http.Request) {
wrec := NewResponseRecorder(w, nil, nil)
w = wrec
+ // wrap the request body in a LengthReader
+ // so we can track the number of bytes read from it
+ var bodyReader *lengthReader
+ if r.Body != nil {
+ bodyReader = &lengthReader{Source: r.Body}
+ r.Body = bodyReader
+ }
+
// capture the original version of the request
accLog := s.accessLogger.With(loggableReq)
@@ -285,7 +294,13 @@ func (s *Server) ServeHTTP(w http.ResponseWriter, r *http.Request) {
userID, _ := repl.GetString("http.auth.user.id")
+ reqBodyLength := 0
+ if bodyReader != nil {
+ reqBodyLength = bodyReader.Length
+ }
+
log("handled request",
+ zap.Int("bytes_read", reqBodyLength),
zap.String("user_id", userID),
zap.Duration("duration", duration),
zap.Int("size", wrec.Size()),
@@ -826,6 +841,23 @@ func cloneURL(from, to *url.URL) {
}
}
+// lengthReader is an io.ReadCloser that keeps track of the
+// number of bytes read from the request body.
+type lengthReader struct {
+ Source io.ReadCloser
+ Length int
+}
+
+func (r *lengthReader) Read(b []byte) (int, error) {
+ n, err := r.Source.Read(b)
+ r.Length += n
+ return n, err
+}
+
+func (r *lengthReader) Close() error {
+ return r.Source.Close()
+}
+
// Context keys for HTTP request context values.
const (
// For referencing the server instance