mirror of
https://github.com/golang/go.git
synced 2025-12-08 06:10:04 +00:00
net/http: don't panic after request if Handler sets Request.Body to nil
The Server's server goroutine was panicing (but recovering) when cleaning up after handling a request. It was pretty harmless (it just closed that one connection and didn't kill the whole process) but it was distracting. Updates #13135 Change-Id: I2a0ce9e8b52c8d364e3f4ce245e05c6f8d62df14 Reviewed-on: https://go-review.googlesource.com/16572 Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org> TryBot-Result: Gobot Gobot <gobot@golang.org> Reviewed-by: Andrew Gerrand <adg@golang.org>
This commit is contained in:
parent
9179c9cb5c
commit
b1050542c1
2 changed files with 30 additions and 3 deletions
|
|
@ -3381,6 +3381,31 @@ func TestHandlerFinishSkipBigContentLengthRead(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestHandlerSetsBodyNil(t *testing.T) {
|
||||
defer afterTest(t)
|
||||
ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
|
||||
r.Body = nil
|
||||
fmt.Fprintf(w, "%v", r.RemoteAddr)
|
||||
}))
|
||||
defer ts.Close()
|
||||
get := func() string {
|
||||
res, err := Get(ts.URL)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
defer res.Body.Close()
|
||||
slurp, err := ioutil.ReadAll(res.Body)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
return string(slurp)
|
||||
}
|
||||
a, b := get(), get()
|
||||
if a != b {
|
||||
t.Errorf("Failed to reuse connections between requests: %v vs %v", a, b)
|
||||
}
|
||||
}
|
||||
|
||||
func BenchmarkClientServer(b *testing.B) {
|
||||
b.ReportAllocs()
|
||||
b.StopTimer()
|
||||
|
|
|
|||
|
|
@ -317,8 +317,9 @@ func (cw *chunkWriter) close() {
|
|||
type response struct {
|
||||
conn *conn
|
||||
req *Request // request for this response
|
||||
wroteHeader bool // reply header has been (logically) written
|
||||
wroteContinue bool // 100 Continue response was written
|
||||
reqBody io.ReadCloser
|
||||
wroteHeader bool // reply header has been (logically) written
|
||||
wroteContinue bool // 100 Continue response was written
|
||||
|
||||
w *bufio.Writer // buffers output in chunks to chunkWriter
|
||||
cw chunkWriter
|
||||
|
|
@ -658,6 +659,7 @@ func (c *conn) readRequest() (w *response, err error) {
|
|||
w = &response{
|
||||
conn: c,
|
||||
req: req,
|
||||
reqBody: req.Body,
|
||||
handlerHeader: make(Header),
|
||||
contentLength: -1,
|
||||
}
|
||||
|
|
@ -1167,7 +1169,7 @@ func (w *response) finishRequest() {
|
|||
|
||||
// Close the body (regardless of w.closeAfterReply) so we can
|
||||
// re-use its bufio.Reader later safely.
|
||||
w.req.Body.Close()
|
||||
w.reqBody.Close()
|
||||
|
||||
if w.req.MultipartForm != nil {
|
||||
w.req.MultipartForm.RemoveAll()
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue