mirror of
https://github.com/yusing/godoxy.git
synced 2026-04-27 18:57:04 +02:00
fix(middleware): allow HTML rewrite for chunked and unknown-length bodies
Relax response-body gating so HTML and XHTML can be buffered when Transfer-Encoding is chunked-only, or when Content-Length is missing, while still rejecting non-identity encodings that are not chunked HTML and other non-HTML cases. Update modifyHTML to cap reads for unknown length, splice the original stream back when the cap is hit, and document the behavior in the package README. Extend tests for themed middleware and the rewrite gate.
This commit is contained in:
@@ -126,7 +126,7 @@ func TestMiddlewareResponseRewriteGate(t *testing.T) {
|
||||
expectBody: "binary",
|
||||
},
|
||||
{
|
||||
name: "block_body_rewrite_for_transfer_encoded_html",
|
||||
name: "allow_body_rewrite_for_transfer_encoded_html",
|
||||
respHeaders: http.Header{
|
||||
"Content-Type": []string{"text/html"},
|
||||
"Transfer-Encoding": []string{"chunked"},
|
||||
@@ -134,6 +134,17 @@ func TestMiddlewareResponseRewriteGate(t *testing.T) {
|
||||
respBody: []byte("<html><body>original</body></html>"),
|
||||
expectStatus: http.StatusTeapot,
|
||||
expectHeader: "1",
|
||||
expectBody: "rewritten-body",
|
||||
},
|
||||
{
|
||||
name: "block_body_rewrite_for_non_chunked_transfer_encoded_html",
|
||||
respHeaders: http.Header{
|
||||
"Content-Type": []string{"text/html"},
|
||||
"Transfer-Encoding": []string{"gzip"},
|
||||
},
|
||||
respBody: []byte("<html><body>original</body></html>"),
|
||||
expectStatus: http.StatusTeapot,
|
||||
expectHeader: "1",
|
||||
expectBody: "<html><body>original</body></html>",
|
||||
},
|
||||
{
|
||||
@@ -208,12 +219,23 @@ func TestMiddlewareResponseRewriteGateServeHTTP(t *testing.T) {
|
||||
expectBody: "binary",
|
||||
},
|
||||
{
|
||||
name: "block_body_rewrite_for_transfer_encoded_html",
|
||||
name: "allow_body_rewrite_for_transfer_encoded_html",
|
||||
respHeaders: http.Header{
|
||||
"Content-Type": []string{"text/html"},
|
||||
"Transfer-Encoding": []string{"chunked"},
|
||||
},
|
||||
respBody: "<html><body>original</body></html>",
|
||||
expectStatusCode: http.StatusTeapot,
|
||||
expectHeader: "1",
|
||||
expectBody: "rewritten-body",
|
||||
},
|
||||
{
|
||||
name: "block_body_rewrite_for_non_chunked_transfer_encoded_html",
|
||||
respHeaders: http.Header{
|
||||
"Content-Type": []string{"text/html"},
|
||||
"Transfer-Encoding": []string{"gzip"},
|
||||
},
|
||||
respBody: "<html><body>original</body></html>",
|
||||
expectStatusCode: http.StatusOK,
|
||||
expectHeader: "",
|
||||
expectBody: "<html><body>original</body></html>",
|
||||
@@ -290,10 +312,10 @@ func TestMiddlewareHeaderRewriteDoesNotBufferLargeBody(t *testing.T) {
|
||||
expect.Equal(t, string(data), "video")
|
||||
}
|
||||
|
||||
func TestThemedSkipsBodyRewriteWhenRewriteBlocked(t *testing.T) {
|
||||
func TestThemedRewritesChunkedHTML(t *testing.T) {
|
||||
result, err := newMiddlewareTest(Themed, &testArgs{
|
||||
middlewareOpt: OptionsRaw{
|
||||
"theme": DarkTheme,
|
||||
"css": "https://example.com/theme.css",
|
||||
},
|
||||
respHeaders: http.Header{
|
||||
"Content-Type": []string{"text/html; charset=utf-8"},
|
||||
@@ -302,5 +324,22 @@ func TestThemedSkipsBodyRewriteWhenRewriteBlocked(t *testing.T) {
|
||||
respBody: []byte("<html><body>original</body></html>"),
|
||||
})
|
||||
expect.NoError(t, err)
|
||||
expect.Equal(t, string(result.Data), "<html><body>original</body></html>")
|
||||
expect.Equal(t, string(result.Data), `<html><head></head><body>original<link rel="stylesheet" href="https://example.com/theme.css"/></body></html>`)
|
||||
}
|
||||
|
||||
func TestThemedSkipsOversizedChunkedHTML(t *testing.T) {
|
||||
originalBody := "<html><body>" + strings.Repeat("a", maxModifiableBody) + "</body></html>"
|
||||
|
||||
result, err := newMiddlewareTest(Themed, &testArgs{
|
||||
middlewareOpt: OptionsRaw{
|
||||
"css": "https://example.com/theme.css",
|
||||
},
|
||||
respHeaders: http.Header{
|
||||
"Content-Type": []string{"text/html; charset=utf-8"},
|
||||
"Transfer-Encoding": []string{"chunked"},
|
||||
},
|
||||
respBody: []byte(originalBody),
|
||||
})
|
||||
expect.NoError(t, err)
|
||||
expect.Equal(t, string(result.Data), originalBody)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user