mirror of https://github.com/golang/go.git
net/http/httputil: ensure DumpRequestOut dumps all of Body
Bodies larger than 8KB (the default bufio reader size) weren't being dumped. Force a read of the body so they're teed into the response buffer. Thanks to Steven Hartland for identifying the problem. Fixes #8089 LGTM=r R=golang-codereviews, r CC=adg, golang-codereviews https://golang.org/cl/144650044
This commit is contained in:
parent
1b89cd1658
commit
4a532c664d
|
|
@ -95,19 +95,27 @@ func DumpRequestOut(req *http.Request, body bool) ([]byte, error) {
|
|||
// with a dummy response.
|
||||
var buf bytes.Buffer // records the output
|
||||
pr, pw := io.Pipe()
|
||||
defer pr.Close()
|
||||
defer pw.Close()
|
||||
dr := &delegateReader{c: make(chan io.Reader)}
|
||||
// Wait for the request before replying with a dummy response:
|
||||
go func() {
|
||||
http.ReadRequest(bufio.NewReader(pr))
|
||||
req, err := http.ReadRequest(bufio.NewReader(pr))
|
||||
if err == nil {
|
||||
// Ensure all the body is read; otherwise
|
||||
// we'll get a partial dump.
|
||||
io.Copy(ioutil.Discard, req.Body)
|
||||
req.Body.Close()
|
||||
}
|
||||
dr.c <- strings.NewReader("HTTP/1.1 204 No Content\r\n\r\n")
|
||||
}()
|
||||
|
||||
t := &http.Transport{
|
||||
DisableKeepAlives: true,
|
||||
Dial: func(net, addr string) (net.Conn, error) {
|
||||
return &dumpConn{io.MultiWriter(&buf, pw), dr}, nil
|
||||
},
|
||||
}
|
||||
defer t.CloseIdleConnections()
|
||||
|
||||
_, err := t.RoundTrip(reqSend)
|
||||
|
||||
|
|
|
|||
|
|
@ -111,6 +111,30 @@ var dumpTests = []dumpTest{
|
|||
|
||||
NoBody: true,
|
||||
},
|
||||
|
||||
// Request with Body > 8196 (default buffer size)
|
||||
{
|
||||
Req: http.Request{
|
||||
Method: "POST",
|
||||
URL: &url.URL{
|
||||
Scheme: "http",
|
||||
Host: "post.tld",
|
||||
Path: "/",
|
||||
},
|
||||
ContentLength: 8193,
|
||||
ProtoMajor: 1,
|
||||
ProtoMinor: 1,
|
||||
},
|
||||
|
||||
Body: bytes.Repeat([]byte("a"), 8193),
|
||||
|
||||
WantDumpOut: "POST / HTTP/1.1\r\n" +
|
||||
"Host: post.tld\r\n" +
|
||||
"User-Agent: Go 1.1 package http\r\n" +
|
||||
"Content-Length: 8193\r\n" +
|
||||
"Accept-Encoding: gzip\r\n\r\n" +
|
||||
strings.Repeat("a", 8193),
|
||||
},
|
||||
}
|
||||
|
||||
func TestDumpRequest(t *testing.T) {
|
||||
|
|
@ -125,6 +149,8 @@ func TestDumpRequest(t *testing.T) {
|
|||
tt.Req.Body = ioutil.NopCloser(bytes.NewReader(b))
|
||||
case func() io.ReadCloser:
|
||||
tt.Req.Body = b()
|
||||
default:
|
||||
t.Fatalf("Test %d: unsupported Body of %T", i, tt.Body)
|
||||
}
|
||||
}
|
||||
setBody()
|
||||
|
|
@ -159,7 +185,9 @@ func TestDumpRequest(t *testing.T) {
|
|||
}
|
||||
}
|
||||
if dg := runtime.NumGoroutine() - numg0; dg > 4 {
|
||||
t.Errorf("Unexpectedly large number of new goroutines: %d new", dg)
|
||||
buf := make([]byte, 4096)
|
||||
buf = buf[:runtime.Stack(buf, true)]
|
||||
t.Errorf("Unexpectedly large number of new goroutines: %d new: %s", dg, buf)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue