Skip to content

net/http: redirection response has closed body #10069

Description

@JamesDunne
  1. What version of Go are you using (go version)?
    go version go1.4.2 darwin/amd64
  2. What operating system and processor architecture are you using?
    Not really relevant to this issue...
    MacBook Pro (15-inch, Mid 2012)
    2.6 GHz Intel Core i7
    16 GB 1600 MHz DDR3
  3. What did you do?
    Implemented a custom redirection policy handler via http.Client's CheckRedirect to stop redirection.
    After a Do() call on a request, the returned response's Body is not nil and reading from it returns an error http: read on closed response body. See example code below.
  4. What did you expect to see?
    Expected either an unclosed, unread-from non-nil Body, or a nil Body.
  5. What did you see instead?
    Saw a closed, already-read-from Body that was not nil.

This unexpected condition required me to hack around the case by explicitly setting resp.Body to nil when detecting my custom redirect policy abort error from the returned url.Error.

Also, I have no access to the intermediate redirection responses. I would want an interception function to be able to inspect the redirection response to see if I should redirect or not, but instead I get a request instance; what good is the request to determine if I should redirect? This design also prevents me from logging relevant redirection details to the end user, so as to properly trace the request-response path.

// Define our redirection policy:
const redirects_max_follow = 0 // for this test case
var redirectPolicyError = errors.New("redirect policy")
client := &http.Client{
    CheckRedirect: func(req *http.Request, via []*http.Request) error {
        if len(via) > redirects_max_follow {
            return redirectPolicyError
        }
        return nil
    },
}

// Make the request:
resp, err := client.Do(req)
if err != nil {
    if uerr, ok := err.(*url.Error); ok {
        if uerr.Err == redirectPolicyError {
            // Redirection responses get their bodies removed by `Do()` automatically.
            // Not sure if this is a bug or not.
            // Setting Body to nil prevents future "http: read on closed response body" error.
            resp.Body = nil
            goto ok
        }
    }
    Error("HTTP error: %s\n", err)
    return -2
ok:
}

No activity

Activity on this issue will appear here.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

      Milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions