• Brad Fitzpatrick's avatar
    net/http: reuse HTTP/1 Transport conns more for gzipped responses · 18072adb
    Brad Fitzpatrick authored
    Flip around the composition order of the http.Response.Body's
    gzip.Reader vs. the reader which keeps track of waiting to see the end
    of the HTTP/1 response framing (whether that's a Content-Length or
    HTTP/1.1 chunking).
    
    Previously:
    
    user -> http.Response.Body
         -> bodyEOFSignal
         -> gzipReader
         -> gzip.Reader
         -> bufio.Reader
       [ -> http/1.1 de-chunking reader ]   optional
         -> http1 framing *body
    
    But because bodyEOFSignal was waiting to see an EOF from the
    underlying gzip.Reader before reusing the connection, and gzip.Reader
    (or more specifically: the flate.Reader) wasn't returning an early
    io.EOF with the final chunk, the bodyEOfSignal was never releasing the
    connection, because the EOF from the http1 framing was read by a party
    who didn't care about it yet: the helper bufio.Reader created to do
    byte-at-a-time reading in the flate.Reader.
    
    Flip the read composition around to:
    
    user -> http.Response.Body
         -> gzipReader
         -> gzip.Reader
         -> bufio.Reader
         -> bodyEOFSignal
       [ -> http/1.1 de-chunking reader ]   optional
         -> http1 framing *body
    
    Now when gzip.Reader does its byte-at-a-time reading via the
    bufio.Reader, the bufio.Reader will do its big reads against the
    bodyEOFSignal reader instead, which will then see the underlying http1
    framing EOF, and be able to reuse the connection.
    
    Updates google/go-github#317
    Updates #14867
    And related abandoned fix to flate.Reader: https://golang.org/cl/21290
    
    Change-Id: I3729dfdffe832ad943b84f4734b0f59b0e834749
    Reviewed-on: https://go-review.googlesource.com/21291Reviewed-by: 's avatarDavid Symonds <dsymonds@golang.org>
    Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
    TryBot-Result: Gobot Gobot <gobot@golang.org>
    18072adb
transport_test.go 81.2 KB