diff options
Diffstat (limited to 'libgo/go/net/http')
-rw-r--r-- | libgo/go/net/http/client.go | 5 | ||||
-rw-r--r-- | libgo/go/net/http/client_test.go | 25 | ||||
-rw-r--r-- | libgo/go/net/http/proxy_test.go | 30 | ||||
-rw-r--r-- | libgo/go/net/http/response.go | 9 | ||||
-rw-r--r-- | libgo/go/net/http/response_test.go | 15 | ||||
-rw-r--r-- | libgo/go/net/http/server.go | 2 | ||||
-rw-r--r-- | libgo/go/net/http/transfer.go | 6 | ||||
-rw-r--r-- | libgo/go/net/http/transport.go | 6 |
8 files changed, 91 insertions, 7 deletions
diff --git a/libgo/go/net/http/client.go b/libgo/go/net/http/client.go index 5d450258bd3..54564e0989e 100644 --- a/libgo/go/net/http/client.go +++ b/libgo/go/net/http/client.go @@ -278,6 +278,11 @@ func (c *Client) Post(url string, bodyType string, body io.Reader) (r *Response, return nil, err } req.Header.Set("Content-Type", bodyType) + if c.Jar != nil { + for _, cookie := range c.Jar.Cookies(req.URL) { + req.AddCookie(cookie) + } + } r, err = send(req, c.Transport) if err == nil && c.Jar != nil { c.Jar.SetCookies(req.URL, r.Cookies()) diff --git a/libgo/go/net/http/client_test.go b/libgo/go/net/http/client_test.go index e00b62e590a..9b4261b9f61 100644 --- a/libgo/go/net/http/client_test.go +++ b/libgo/go/net/http/client_test.go @@ -256,6 +256,31 @@ var echoCookiesRedirectHandler = HandlerFunc(func(w ResponseWriter, r *Request) } }) +func TestClientSendsCookieFromJar(t *testing.T) { + tr := &recordingTransport{} + client := &Client{Transport: tr} + client.Jar = &TestJar{perURL: make(map[string][]*Cookie)} + us := "http://dummy.faketld/" + u, _ := url.Parse(us) + client.Jar.SetCookies(u, expectedCookies) + + client.Get(us) // Note: doesn't hit network + matchReturnedCookies(t, expectedCookies, tr.req.Cookies()) + + client.Head(us) // Note: doesn't hit network + matchReturnedCookies(t, expectedCookies, tr.req.Cookies()) + + client.Post(us, "text/plain", strings.NewReader("body")) // Note: doesn't hit network + matchReturnedCookies(t, expectedCookies, tr.req.Cookies()) + + client.PostForm(us, url.Values{}) // Note: doesn't hit network + matchReturnedCookies(t, expectedCookies, tr.req.Cookies()) + + req, _ := NewRequest("GET", us, nil) + client.Do(req) // Note: doesn't hit network + matchReturnedCookies(t, expectedCookies, tr.req.Cookies()) +} + // Just enough correctness for our redirect tests. Uses the URL.Host as the // scope of all cookies. type TestJar struct { diff --git a/libgo/go/net/http/proxy_test.go b/libgo/go/net/http/proxy_test.go index 9b320b3aa5b..5ecffaface9 100644 --- a/libgo/go/net/http/proxy_test.go +++ b/libgo/go/net/http/proxy_test.go @@ -5,6 +5,7 @@ package http import ( + "net/url" "os" "testing" ) @@ -46,3 +47,32 @@ func TestUseProxy(t *testing.T) { } } } + +var cacheKeysTests = []struct { + proxy string + scheme string + addr string + key string +}{ + {"", "http", "foo.com", "|http|foo.com"}, + {"", "https", "foo.com", "|https|foo.com"}, + {"http://foo.com", "http", "foo.com", "http://foo.com|http|"}, + {"http://foo.com", "https", "foo.com", "http://foo.com|https|foo.com"}, +} + +func TestCacheKeys(t *testing.T) { + for _, tt := range cacheKeysTests { + var proxy *url.URL + if tt.proxy != "" { + u, err := url.Parse(tt.proxy) + if err != nil { + t.Fatal(err) + } + proxy = u + } + cm := connectMethod{proxy, tt.scheme, tt.addr} + if cm.String() != tt.key { + t.Fatalf("{%q, %q, %q} cache key %q; want %q", tt.proxy, tt.scheme, tt.addr, cm.String(), tt.key) + } + } +} diff --git a/libgo/go/net/http/response.go b/libgo/go/net/http/response.go index b7902209786..945ecd8a4b0 100644 --- a/libgo/go/net/http/response.go +++ b/libgo/go/net/http/response.go @@ -202,9 +202,12 @@ func (r *Response) Write(w io.Writer) error { text = "status code " + strconv.Itoa(r.StatusCode) } } - io.WriteString(w, "HTTP/"+strconv.Itoa(r.ProtoMajor)+".") - io.WriteString(w, strconv.Itoa(r.ProtoMinor)+" ") - io.WriteString(w, strconv.Itoa(r.StatusCode)+" "+text+"\r\n") + protoMajor, protoMinor := strconv.Itoa(r.ProtoMajor), strconv.Itoa(r.ProtoMinor) + statusCode := strconv.Itoa(r.StatusCode) + " " + if strings.HasPrefix(text, statusCode) { + text = text[len(statusCode):] + } + io.WriteString(w, "HTTP/"+protoMajor+"."+protoMinor+" "+statusCode+text+"\r\n") // Process Body,ContentLength,Close,Trailer tw, err := newTransferWriter(r) diff --git a/libgo/go/net/http/response_test.go b/libgo/go/net/http/response_test.go index 165ec3624a4..6eed4887ddc 100644 --- a/libgo/go/net/http/response_test.go +++ b/libgo/go/net/http/response_test.go @@ -14,6 +14,7 @@ import ( "io/ioutil" "net/url" "reflect" + "strings" "testing" ) @@ -444,3 +445,17 @@ func TestLocationResponse(t *testing.T) { } } } + +func TestResponseStatusStutter(t *testing.T) { + r := &Response{ + Status: "123 some status", + StatusCode: 123, + ProtoMajor: 1, + ProtoMinor: 3, + } + var buf bytes.Buffer + r.Write(&buf) + if strings.Contains(buf.String(), "123 123") { + t.Errorf("stutter in status: %s", buf.String()) + } +} diff --git a/libgo/go/net/http/server.go b/libgo/go/net/http/server.go index 924ffd34815..0572b4ae347 100644 --- a/libgo/go/net/http/server.go +++ b/libgo/go/net/http/server.go @@ -31,7 +31,7 @@ import ( // Errors introduced by the HTTP server. var ( ErrWriteAfterFlush = errors.New("Conn.Write called after Flush") - ErrBodyNotAllowed = errors.New("http: response status code does not allow body") + ErrBodyNotAllowed = errors.New("http: request method or response status code does not allow body") ErrHijacked = errors.New("Conn has been hijacked") ErrContentLength = errors.New("Conn.Write wrote more than the declared Content-Length") ) diff --git a/libgo/go/net/http/transfer.go b/libgo/go/net/http/transfer.go index 3c8fe7f5b51..9e9d84172d0 100644 --- a/libgo/go/net/http/transfer.go +++ b/libgo/go/net/http/transfer.go @@ -71,7 +71,9 @@ func newTransferWriter(r interface{}) (t *transferWriter, err error) { } } case *Response: - t.Method = rr.Request.Method + if rr.Request != nil { + t.Method = rr.Request.Method + } t.Body = rr.Body t.BodyCloser = rr.Body t.ContentLength = rr.ContentLength @@ -79,7 +81,7 @@ func newTransferWriter(r interface{}) (t *transferWriter, err error) { t.TransferEncoding = rr.TransferEncoding t.Trailer = rr.Trailer atLeastHTTP11 = rr.ProtoAtLeast(1, 1) - t.ResponseToHEAD = noBodyExpected(rr.Request.Method) + t.ResponseToHEAD = noBodyExpected(t.Method) } // Sanitize Body,ContentLength,TransferEncoding diff --git a/libgo/go/net/http/transport.go b/libgo/go/net/http/transport.go index 024975946e5..6efe191eb0b 100644 --- a/libgo/go/net/http/transport.go +++ b/libgo/go/net/http/transport.go @@ -450,10 +450,14 @@ type connectMethod struct { func (ck *connectMethod) String() string { proxyStr := "" + targetAddr := ck.targetAddr if ck.proxyURL != nil { proxyStr = ck.proxyURL.String() + if ck.targetScheme == "http" { + targetAddr = "" + } } - return strings.Join([]string{proxyStr, ck.targetScheme, ck.targetAddr}, "|") + return strings.Join([]string{proxyStr, ck.targetScheme, targetAddr}, "|") } // addr returns the first hop "host:port" to which we need to TCP connect. |