fix(http): honour template max-size under global response-size-read limit

When -response-size-read (-rsr) is configured, use it as a ceiling while
preserving a template's own MaxSize when smaller, rather than unconditionally
overwriting it. Also account for ResponseReadSize in response truncation detection.

Fixes #7873
This commit is contained in:
TassioSales committed 2026-10-20 21:07:35 -03:00
1 parent b0eeadc554
commit c918d010c5
2 files changed
+84 -2

No files matched your search

+7 -2
View File
@@ -1342,7 +1342,11 @@ func (request *Request) executeRequest(input *contextargs.Context, generatedRequ
maxBodylimit = request.MaxSize
}
if request.options.Options.ResponseReadSize != 0 {
maxBodylimit = request.options.Options.ResponseReadSize
if request.MaxSize > 0 {
maxBodylimit = min(request.MaxSize, request.options.Options.ResponseReadSize)
} else {
maxBodylimit = request.options.Options.ResponseReadSize
}
}
// respChain is http response chain that reads response body
@@ -1523,7 +1527,8 @@ func (request *Request) executeRequest(input *contextargs.Context, generatedRequ
}
responseContentType := respChain.Response().Header.Get("Content-Type")
isResponseTruncated := request.MaxSize > 0 && respChain.Body().Len() >= request.MaxSize
isResponseTruncated := (request.MaxSize > 0 && respChain.Body().Len() >= request.MaxSize) ||
(request.options.Options.ResponseReadSize > 0 && respChain.Body().Len() >= request.options.Options.ResponseReadSize)
dumpResponse(event, request, fullResponseStr, formedURL, responseContentType, isResponseTruncated, input.MetaInput.Input)
callback(event)
+77
View File
@@ -1659,3 +1659,80 @@ func TestReuseRequestBodyKeepsExcludedEncoding(t *testing.T) {
})
}
}
func TestHTTPResponseReadSizeHonoursTemplateMaxSize(t *testing.T) {
ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
w.Header().Set("Content-Type", "text/plain")
_, _ = w.Write([]byte(strings.Repeat("A", 2000)))
}))
defer ts.Close()
tests := []struct {
name string
templateMaxSize int
globalResponseReadSize int
expectedLen int
}{
{
name: "template max-size smaller than global response-size-read",
templateMaxSize: 500,
globalResponseReadSize: 1000,
expectedLen: 500,
},
{
name: "global response-size-read acts as ceiling when smaller than template max-size",
templateMaxSize: 1500,
globalResponseReadSize: 800,
expectedLen: 800,
},
{
name: "only template max-size specified",
templateMaxSize: 500,
globalResponseReadSize: 0,
expectedLen: 500,
},
{
name: "only global response-size-read specified",
templateMaxSize: 0,
globalResponseReadSize: 600,
expectedLen: 600,
},
}
for _, tc := range tests {
t.Run(tc.name, func(t *testing.T) {
opts := testutils.DefaultOptions
opts.ResponseReadSize = tc.globalResponseReadSize
testutils.Init(opts)
request := &Request{
ID: "test-max-size",
MaxSize: tc.templateMaxSize,
Raw: []string{
"GET / HTTP/1.1\nHost: {{Hostname}}\n\n",
},
}
executerOptions := testutils.NewMockExecuterOptions(opts, &testutils.TemplateInfo{
ID: request.ID,
Info: model.Info{SeverityHolder: severity.Holder{Severity: severity.Low}, Name: "test"},
})
require.NoError(t, request.Compile(executerOptions))
var receivedBodyLen int
err := request.ExecuteWithResults(
contextargs.NewWithInput(context.Background(), ts.URL),
make(output.InternalEvent),
make(output.InternalEvent),
func(event *output.InternalWrappedEvent) {
if event != nil && event.InternalEvent != nil {
if body, ok := event.InternalEvent["body"].(string); ok {
receivedBodyLen = len(body)
}
}
},
)
require.NoError(t, err)
require.Equal(t, tc.expectedLen, receivedBodyLen)
})
}
}