github.com/fjballest/golang@v0.0.0-20151209143359-e4c5fe594ca8/src/net/http/transport_test.go (about)

     1  // Copyright 2011 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  // Tests for transport.go.
     6  //
     7  // More tests are in clientserver_test.go (for things testing both client & server for both
     8  // HTTP/1 and HTTP/2). This
     9  
    10  package http_test
    11  
    12  import (
    13  	"bufio"
    14  	"bytes"
    15  	"compress/gzip"
    16  	"crypto/rand"
    17  	"crypto/tls"
    18  	"errors"
    19  	"fmt"
    20  	"io"
    21  	"io/ioutil"
    22  	"log"
    23  	"net"
    24  	. "net/http"
    25  	"net/http/httptest"
    26  	"net/http/httputil"
    27  	"net/url"
    28  	"os"
    29  	"reflect"
    30  	"runtime"
    31  	"strconv"
    32  	"strings"
    33  	"sync"
    34  	"testing"
    35  	"time"
    36  )
    37  
    38  // TODO: test 5 pipelined requests with responses: 1) OK, 2) OK, Connection: Close
    39  //       and then verify that the final 2 responses get errors back.
    40  
    41  // hostPortHandler writes back the client's "host:port".
    42  var hostPortHandler = HandlerFunc(func(w ResponseWriter, r *Request) {
    43  	if r.FormValue("close") == "true" {
    44  		w.Header().Set("Connection", "close")
    45  	}
    46  	w.Header().Set("X-Saw-Close", fmt.Sprint(r.Close))
    47  	w.Write([]byte(r.RemoteAddr))
    48  })
    49  
    50  // testCloseConn is a net.Conn tracked by a testConnSet.
    51  type testCloseConn struct {
    52  	net.Conn
    53  	set *testConnSet
    54  }
    55  
    56  func (c *testCloseConn) Close() error {
    57  	c.set.remove(c)
    58  	return c.Conn.Close()
    59  }
    60  
    61  // testConnSet tracks a set of TCP connections and whether they've
    62  // been closed.
    63  type testConnSet struct {
    64  	t      *testing.T
    65  	mu     sync.Mutex // guards closed and list
    66  	closed map[net.Conn]bool
    67  	list   []net.Conn // in order created
    68  }
    69  
    70  func (tcs *testConnSet) insert(c net.Conn) {
    71  	tcs.mu.Lock()
    72  	defer tcs.mu.Unlock()
    73  	tcs.closed[c] = false
    74  	tcs.list = append(tcs.list, c)
    75  }
    76  
    77  func (tcs *testConnSet) remove(c net.Conn) {
    78  	tcs.mu.Lock()
    79  	defer tcs.mu.Unlock()
    80  	tcs.closed[c] = true
    81  }
    82  
    83  // some tests use this to manage raw tcp connections for later inspection
    84  func makeTestDial(t *testing.T) (*testConnSet, func(n, addr string) (net.Conn, error)) {
    85  	connSet := &testConnSet{
    86  		t:      t,
    87  		closed: make(map[net.Conn]bool),
    88  	}
    89  	dial := func(n, addr string) (net.Conn, error) {
    90  		c, err := net.Dial(n, addr)
    91  		if err != nil {
    92  			return nil, err
    93  		}
    94  		tc := &testCloseConn{c, connSet}
    95  		connSet.insert(tc)
    96  		return tc, nil
    97  	}
    98  	return connSet, dial
    99  }
   100  
   101  func (tcs *testConnSet) check(t *testing.T) {
   102  	tcs.mu.Lock()
   103  	defer tcs.mu.Unlock()
   104  	for i := 4; i >= 0; i-- {
   105  		for i, c := range tcs.list {
   106  			if tcs.closed[c] {
   107  				continue
   108  			}
   109  			if i != 0 {
   110  				tcs.mu.Unlock()
   111  				time.Sleep(50 * time.Millisecond)
   112  				tcs.mu.Lock()
   113  				continue
   114  			}
   115  			t.Errorf("TCP connection #%d, %p (of %d total) was not closed", i+1, c, len(tcs.list))
   116  		}
   117  	}
   118  }
   119  
   120  // Two subsequent requests and verify their response is the same.
   121  // The response from the server is our own IP:port
   122  func TestTransportKeepAlives(t *testing.T) {
   123  	defer afterTest(t)
   124  	ts := httptest.NewServer(hostPortHandler)
   125  	defer ts.Close()
   126  
   127  	for _, disableKeepAlive := range []bool{false, true} {
   128  		tr := &Transport{DisableKeepAlives: disableKeepAlive}
   129  		defer tr.CloseIdleConnections()
   130  		c := &Client{Transport: tr}
   131  
   132  		fetch := func(n int) string {
   133  			res, err := c.Get(ts.URL)
   134  			if err != nil {
   135  				t.Fatalf("error in disableKeepAlive=%v, req #%d, GET: %v", disableKeepAlive, n, err)
   136  			}
   137  			body, err := ioutil.ReadAll(res.Body)
   138  			if err != nil {
   139  				t.Fatalf("error in disableKeepAlive=%v, req #%d, ReadAll: %v", disableKeepAlive, n, err)
   140  			}
   141  			return string(body)
   142  		}
   143  
   144  		body1 := fetch(1)
   145  		body2 := fetch(2)
   146  
   147  		bodiesDiffer := body1 != body2
   148  		if bodiesDiffer != disableKeepAlive {
   149  			t.Errorf("error in disableKeepAlive=%v. unexpected bodiesDiffer=%v; body1=%q; body2=%q",
   150  				disableKeepAlive, bodiesDiffer, body1, body2)
   151  		}
   152  	}
   153  }
   154  
   155  func TestTransportConnectionCloseOnResponse(t *testing.T) {
   156  	defer afterTest(t)
   157  	ts := httptest.NewServer(hostPortHandler)
   158  	defer ts.Close()
   159  
   160  	connSet, testDial := makeTestDial(t)
   161  
   162  	for _, connectionClose := range []bool{false, true} {
   163  		tr := &Transport{
   164  			Dial: testDial,
   165  		}
   166  		c := &Client{Transport: tr}
   167  
   168  		fetch := func(n int) string {
   169  			req := new(Request)
   170  			var err error
   171  			req.URL, err = url.Parse(ts.URL + fmt.Sprintf("/?close=%v", connectionClose))
   172  			if err != nil {
   173  				t.Fatalf("URL parse error: %v", err)
   174  			}
   175  			req.Method = "GET"
   176  			req.Proto = "HTTP/1.1"
   177  			req.ProtoMajor = 1
   178  			req.ProtoMinor = 1
   179  
   180  			res, err := c.Do(req)
   181  			if err != nil {
   182  				t.Fatalf("error in connectionClose=%v, req #%d, Do: %v", connectionClose, n, err)
   183  			}
   184  			defer res.Body.Close()
   185  			body, err := ioutil.ReadAll(res.Body)
   186  			if err != nil {
   187  				t.Fatalf("error in connectionClose=%v, req #%d, ReadAll: %v", connectionClose, n, err)
   188  			}
   189  			return string(body)
   190  		}
   191  
   192  		body1 := fetch(1)
   193  		body2 := fetch(2)
   194  		bodiesDiffer := body1 != body2
   195  		if bodiesDiffer != connectionClose {
   196  			t.Errorf("error in connectionClose=%v. unexpected bodiesDiffer=%v; body1=%q; body2=%q",
   197  				connectionClose, bodiesDiffer, body1, body2)
   198  		}
   199  
   200  		tr.CloseIdleConnections()
   201  	}
   202  
   203  	connSet.check(t)
   204  }
   205  
   206  func TestTransportConnectionCloseOnRequest(t *testing.T) {
   207  	defer afterTest(t)
   208  	ts := httptest.NewServer(hostPortHandler)
   209  	defer ts.Close()
   210  
   211  	connSet, testDial := makeTestDial(t)
   212  
   213  	for _, connectionClose := range []bool{false, true} {
   214  		tr := &Transport{
   215  			Dial: testDial,
   216  		}
   217  		c := &Client{Transport: tr}
   218  
   219  		fetch := func(n int) string {
   220  			req := new(Request)
   221  			var err error
   222  			req.URL, err = url.Parse(ts.URL)
   223  			if err != nil {
   224  				t.Fatalf("URL parse error: %v", err)
   225  			}
   226  			req.Method = "GET"
   227  			req.Proto = "HTTP/1.1"
   228  			req.ProtoMajor = 1
   229  			req.ProtoMinor = 1
   230  			req.Close = connectionClose
   231  
   232  			res, err := c.Do(req)
   233  			if err != nil {
   234  				t.Fatalf("error in connectionClose=%v, req #%d, Do: %v", connectionClose, n, err)
   235  			}
   236  			if got, want := res.Header.Get("X-Saw-Close"), fmt.Sprint(connectionClose); got != want {
   237  				t.Errorf("For connectionClose = %v; handler's X-Saw-Close was %v; want %v",
   238  					connectionClose, got, !connectionClose)
   239  			}
   240  			body, err := ioutil.ReadAll(res.Body)
   241  			if err != nil {
   242  				t.Fatalf("error in connectionClose=%v, req #%d, ReadAll: %v", connectionClose, n, err)
   243  			}
   244  			return string(body)
   245  		}
   246  
   247  		body1 := fetch(1)
   248  		body2 := fetch(2)
   249  		bodiesDiffer := body1 != body2
   250  		if bodiesDiffer != connectionClose {
   251  			t.Errorf("error in connectionClose=%v. unexpected bodiesDiffer=%v; body1=%q; body2=%q",
   252  				connectionClose, bodiesDiffer, body1, body2)
   253  		}
   254  
   255  		tr.CloseIdleConnections()
   256  	}
   257  
   258  	connSet.check(t)
   259  }
   260  
   261  // if the Transport's DisableKeepAlives is set, all requests should
   262  // send Connection: close.
   263  // HTTP/1-only (Connection: close doesn't exist in h2)
   264  func TestTransportConnectionCloseOnRequestDisableKeepAlive(t *testing.T) {
   265  	defer afterTest(t)
   266  	ts := httptest.NewServer(hostPortHandler)
   267  	defer ts.Close()
   268  
   269  	tr := &Transport{
   270  		DisableKeepAlives: true,
   271  	}
   272  	c := &Client{Transport: tr}
   273  	res, err := c.Get(ts.URL)
   274  	if err != nil {
   275  		t.Fatal(err)
   276  	}
   277  	res.Body.Close()
   278  	if res.Header.Get("X-Saw-Close") != "true" {
   279  		t.Errorf("handler didn't see Connection: close ")
   280  	}
   281  }
   282  
   283  func TestTransportIdleCacheKeys(t *testing.T) {
   284  	defer afterTest(t)
   285  	ts := httptest.NewServer(hostPortHandler)
   286  	defer ts.Close()
   287  
   288  	tr := &Transport{DisableKeepAlives: false}
   289  	c := &Client{Transport: tr}
   290  
   291  	if e, g := 0, len(tr.IdleConnKeysForTesting()); e != g {
   292  		t.Errorf("After CloseIdleConnections expected %d idle conn cache keys; got %d", e, g)
   293  	}
   294  
   295  	resp, err := c.Get(ts.URL)
   296  	if err != nil {
   297  		t.Error(err)
   298  	}
   299  	ioutil.ReadAll(resp.Body)
   300  
   301  	keys := tr.IdleConnKeysForTesting()
   302  	if e, g := 1, len(keys); e != g {
   303  		t.Fatalf("After Get expected %d idle conn cache keys; got %d", e, g)
   304  	}
   305  
   306  	if e := "|http|" + ts.Listener.Addr().String(); keys[0] != e {
   307  		t.Errorf("Expected idle cache key %q; got %q", e, keys[0])
   308  	}
   309  
   310  	tr.CloseIdleConnections()
   311  	if e, g := 0, len(tr.IdleConnKeysForTesting()); e != g {
   312  		t.Errorf("After CloseIdleConnections expected %d idle conn cache keys; got %d", e, g)
   313  	}
   314  }
   315  
   316  // Tests that the HTTP transport re-uses connections when a client
   317  // reads to the end of a response Body without closing it.
   318  func TestTransportReadToEndReusesConn(t *testing.T) {
   319  	defer afterTest(t)
   320  	const msg = "foobar"
   321  
   322  	var addrSeen map[string]int
   323  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   324  		addrSeen[r.RemoteAddr]++
   325  		if r.URL.Path == "/chunked/" {
   326  			w.WriteHeader(200)
   327  			w.(Flusher).Flush()
   328  		} else {
   329  			w.Header().Set("Content-Type", strconv.Itoa(len(msg)))
   330  			w.WriteHeader(200)
   331  		}
   332  		w.Write([]byte(msg))
   333  	}))
   334  	defer ts.Close()
   335  
   336  	buf := make([]byte, len(msg))
   337  
   338  	for pi, path := range []string{"/content-length/", "/chunked/"} {
   339  		wantLen := []int{len(msg), -1}[pi]
   340  		addrSeen = make(map[string]int)
   341  		for i := 0; i < 3; i++ {
   342  			res, err := Get(ts.URL + path)
   343  			if err != nil {
   344  				t.Errorf("Get %s: %v", path, err)
   345  				continue
   346  			}
   347  			// We want to close this body eventually (before the
   348  			// defer afterTest at top runs), but not before the
   349  			// len(addrSeen) check at the bottom of this test,
   350  			// since Closing this early in the loop would risk
   351  			// making connections be re-used for the wrong reason.
   352  			defer res.Body.Close()
   353  
   354  			if res.ContentLength != int64(wantLen) {
   355  				t.Errorf("%s res.ContentLength = %d; want %d", path, res.ContentLength, wantLen)
   356  			}
   357  			n, err := res.Body.Read(buf)
   358  			if n != len(msg) || err != io.EOF {
   359  				t.Errorf("%s Read = %v, %v; want %d, EOF", path, n, err, len(msg))
   360  			}
   361  		}
   362  		if len(addrSeen) != 1 {
   363  			t.Errorf("for %s, server saw %d distinct client addresses; want 1", path, len(addrSeen))
   364  		}
   365  	}
   366  }
   367  
   368  func TestTransportMaxPerHostIdleConns(t *testing.T) {
   369  	defer afterTest(t)
   370  	resch := make(chan string)
   371  	gotReq := make(chan bool)
   372  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   373  		gotReq <- true
   374  		msg := <-resch
   375  		_, err := w.Write([]byte(msg))
   376  		if err != nil {
   377  			t.Fatalf("Write: %v", err)
   378  		}
   379  	}))
   380  	defer ts.Close()
   381  	maxIdleConns := 2
   382  	tr := &Transport{DisableKeepAlives: false, MaxIdleConnsPerHost: maxIdleConns}
   383  	c := &Client{Transport: tr}
   384  
   385  	// Start 3 outstanding requests and wait for the server to get them.
   386  	// Their responses will hang until we write to resch, though.
   387  	donech := make(chan bool)
   388  	doReq := func() {
   389  		resp, err := c.Get(ts.URL)
   390  		if err != nil {
   391  			t.Error(err)
   392  			return
   393  		}
   394  		if _, err := ioutil.ReadAll(resp.Body); err != nil {
   395  			t.Errorf("ReadAll: %v", err)
   396  			return
   397  		}
   398  		donech <- true
   399  	}
   400  	go doReq()
   401  	<-gotReq
   402  	go doReq()
   403  	<-gotReq
   404  	go doReq()
   405  	<-gotReq
   406  
   407  	if e, g := 0, len(tr.IdleConnKeysForTesting()); e != g {
   408  		t.Fatalf("Before writes, expected %d idle conn cache keys; got %d", e, g)
   409  	}
   410  
   411  	resch <- "res1"
   412  	<-donech
   413  	keys := tr.IdleConnKeysForTesting()
   414  	if e, g := 1, len(keys); e != g {
   415  		t.Fatalf("after first response, expected %d idle conn cache keys; got %d", e, g)
   416  	}
   417  	cacheKey := "|http|" + ts.Listener.Addr().String()
   418  	if keys[0] != cacheKey {
   419  		t.Fatalf("Expected idle cache key %q; got %q", cacheKey, keys[0])
   420  	}
   421  	if e, g := 1, tr.IdleConnCountForTesting(cacheKey); e != g {
   422  		t.Errorf("after first response, expected %d idle conns; got %d", e, g)
   423  	}
   424  
   425  	resch <- "res2"
   426  	<-donech
   427  	if e, g := 2, tr.IdleConnCountForTesting(cacheKey); e != g {
   428  		t.Errorf("after second response, expected %d idle conns; got %d", e, g)
   429  	}
   430  
   431  	resch <- "res3"
   432  	<-donech
   433  	if e, g := maxIdleConns, tr.IdleConnCountForTesting(cacheKey); e != g {
   434  		t.Errorf("after third response, still expected %d idle conns; got %d", e, g)
   435  	}
   436  }
   437  
   438  func TestTransportServerClosingUnexpectedly(t *testing.T) {
   439  	defer afterTest(t)
   440  	ts := httptest.NewServer(hostPortHandler)
   441  	defer ts.Close()
   442  
   443  	tr := &Transport{}
   444  	c := &Client{Transport: tr}
   445  
   446  	fetch := func(n, retries int) string {
   447  		condFatalf := func(format string, arg ...interface{}) {
   448  			if retries <= 0 {
   449  				t.Fatalf(format, arg...)
   450  			}
   451  			t.Logf("retrying shortly after expected error: "+format, arg...)
   452  			time.Sleep(time.Second / time.Duration(retries))
   453  		}
   454  		for retries >= 0 {
   455  			retries--
   456  			res, err := c.Get(ts.URL)
   457  			if err != nil {
   458  				condFatalf("error in req #%d, GET: %v", n, err)
   459  				continue
   460  			}
   461  			body, err := ioutil.ReadAll(res.Body)
   462  			if err != nil {
   463  				condFatalf("error in req #%d, ReadAll: %v", n, err)
   464  				continue
   465  			}
   466  			res.Body.Close()
   467  			return string(body)
   468  		}
   469  		panic("unreachable")
   470  	}
   471  
   472  	body1 := fetch(1, 0)
   473  	body2 := fetch(2, 0)
   474  
   475  	ts.CloseClientConnections() // surprise!
   476  
   477  	// This test has an expected race. Sleeping for 25 ms prevents
   478  	// it on most fast machines, causing the next fetch() call to
   479  	// succeed quickly.  But if we do get errors, fetch() will retry 5
   480  	// times with some delays between.
   481  	time.Sleep(25 * time.Millisecond)
   482  
   483  	body3 := fetch(3, 5)
   484  
   485  	if body1 != body2 {
   486  		t.Errorf("expected body1 and body2 to be equal")
   487  	}
   488  	if body2 == body3 {
   489  		t.Errorf("expected body2 and body3 to be different")
   490  	}
   491  }
   492  
   493  // Test for https://golang.org/issue/2616 (appropriate issue number)
   494  // This fails pretty reliably with GOMAXPROCS=100 or something high.
   495  func TestStressSurpriseServerCloses(t *testing.T) {
   496  	defer afterTest(t)
   497  	if testing.Short() {
   498  		t.Skip("skipping test in short mode")
   499  	}
   500  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   501  		w.Header().Set("Content-Length", "5")
   502  		w.Header().Set("Content-Type", "text/plain")
   503  		w.Write([]byte("Hello"))
   504  		w.(Flusher).Flush()
   505  		conn, buf, _ := w.(Hijacker).Hijack()
   506  		buf.Flush()
   507  		conn.Close()
   508  	}))
   509  	defer ts.Close()
   510  
   511  	tr := &Transport{DisableKeepAlives: false}
   512  	c := &Client{Transport: tr}
   513  	defer tr.CloseIdleConnections()
   514  
   515  	// Do a bunch of traffic from different goroutines. Send to activityc
   516  	// after each request completes, regardless of whether it failed.
   517  	// If these are too high, OS X exhausts its ephemeral ports
   518  	// and hangs waiting for them to transition TCP states. That's
   519  	// not what we want to test.  TODO(bradfitz): use an io.Pipe
   520  	// dialer for this test instead?
   521  	const (
   522  		numClients    = 20
   523  		reqsPerClient = 25
   524  	)
   525  	activityc := make(chan bool)
   526  	for i := 0; i < numClients; i++ {
   527  		go func() {
   528  			for i := 0; i < reqsPerClient; i++ {
   529  				res, err := c.Get(ts.URL)
   530  				if err == nil {
   531  					// We expect errors since the server is
   532  					// hanging up on us after telling us to
   533  					// send more requests, so we don't
   534  					// actually care what the error is.
   535  					// But we want to close the body in cases
   536  					// where we won the race.
   537  					res.Body.Close()
   538  				}
   539  				activityc <- true
   540  			}
   541  		}()
   542  	}
   543  
   544  	// Make sure all the request come back, one way or another.
   545  	for i := 0; i < numClients*reqsPerClient; i++ {
   546  		select {
   547  		case <-activityc:
   548  		case <-time.After(5 * time.Second):
   549  			t.Fatalf("presumed deadlock; no HTTP client activity seen in awhile")
   550  		}
   551  	}
   552  }
   553  
   554  // TestTransportHeadResponses verifies that we deal with Content-Lengths
   555  // with no bodies properly
   556  func TestTransportHeadResponses(t *testing.T) {
   557  	defer afterTest(t)
   558  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   559  		if r.Method != "HEAD" {
   560  			panic("expected HEAD; got " + r.Method)
   561  		}
   562  		w.Header().Set("Content-Length", "123")
   563  		w.WriteHeader(200)
   564  	}))
   565  	defer ts.Close()
   566  
   567  	tr := &Transport{DisableKeepAlives: false}
   568  	c := &Client{Transport: tr}
   569  	for i := 0; i < 2; i++ {
   570  		res, err := c.Head(ts.URL)
   571  		if err != nil {
   572  			t.Errorf("error on loop %d: %v", i, err)
   573  			continue
   574  		}
   575  		if e, g := "123", res.Header.Get("Content-Length"); e != g {
   576  			t.Errorf("loop %d: expected Content-Length header of %q, got %q", i, e, g)
   577  		}
   578  		if e, g := int64(123), res.ContentLength; e != g {
   579  			t.Errorf("loop %d: expected res.ContentLength of %v, got %v", i, e, g)
   580  		}
   581  		if all, err := ioutil.ReadAll(res.Body); err != nil {
   582  			t.Errorf("loop %d: Body ReadAll: %v", i, err)
   583  		} else if len(all) != 0 {
   584  			t.Errorf("Bogus body %q", all)
   585  		}
   586  	}
   587  }
   588  
   589  // TestTransportHeadChunkedResponse verifies that we ignore chunked transfer-encoding
   590  // on responses to HEAD requests.
   591  func TestTransportHeadChunkedResponse(t *testing.T) {
   592  	defer afterTest(t)
   593  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   594  		if r.Method != "HEAD" {
   595  			panic("expected HEAD; got " + r.Method)
   596  		}
   597  		w.Header().Set("Transfer-Encoding", "chunked") // client should ignore
   598  		w.Header().Set("x-client-ipport", r.RemoteAddr)
   599  		w.WriteHeader(200)
   600  	}))
   601  	defer ts.Close()
   602  
   603  	tr := &Transport{DisableKeepAlives: false}
   604  	c := &Client{Transport: tr}
   605  
   606  	// Ensure that we wait for the readLoop to complete before
   607  	// calling Head again
   608  	didRead := make(chan bool)
   609  	SetReadLoopBeforeNextReadHook(func() { didRead <- true })
   610  	defer SetReadLoopBeforeNextReadHook(nil)
   611  
   612  	res1, err := c.Head(ts.URL)
   613  	<-didRead
   614  
   615  	if err != nil {
   616  		t.Fatalf("request 1 error: %v", err)
   617  	}
   618  
   619  	res2, err := c.Head(ts.URL)
   620  	<-didRead
   621  
   622  	if err != nil {
   623  		t.Fatalf("request 2 error: %v", err)
   624  	}
   625  	if v1, v2 := res1.Header.Get("x-client-ipport"), res2.Header.Get("x-client-ipport"); v1 != v2 {
   626  		t.Errorf("ip/ports differed between head requests: %q vs %q", v1, v2)
   627  	}
   628  }
   629  
   630  var roundTripTests = []struct {
   631  	accept       string
   632  	expectAccept string
   633  	compressed   bool
   634  }{
   635  	// Requests with no accept-encoding header use transparent compression
   636  	{"", "gzip", false},
   637  	// Requests with other accept-encoding should pass through unmodified
   638  	{"foo", "foo", false},
   639  	// Requests with accept-encoding == gzip should be passed through
   640  	{"gzip", "gzip", true},
   641  }
   642  
   643  // Test that the modification made to the Request by the RoundTripper is cleaned up
   644  func TestRoundTripGzip(t *testing.T) {
   645  	defer afterTest(t)
   646  	const responseBody = "test response body"
   647  	ts := httptest.NewServer(HandlerFunc(func(rw ResponseWriter, req *Request) {
   648  		accept := req.Header.Get("Accept-Encoding")
   649  		if expect := req.FormValue("expect_accept"); accept != expect {
   650  			t.Errorf("in handler, test %v: Accept-Encoding = %q, want %q",
   651  				req.FormValue("testnum"), accept, expect)
   652  		}
   653  		if accept == "gzip" {
   654  			rw.Header().Set("Content-Encoding", "gzip")
   655  			gz := gzip.NewWriter(rw)
   656  			gz.Write([]byte(responseBody))
   657  			gz.Close()
   658  		} else {
   659  			rw.Header().Set("Content-Encoding", accept)
   660  			rw.Write([]byte(responseBody))
   661  		}
   662  	}))
   663  	defer ts.Close()
   664  
   665  	for i, test := range roundTripTests {
   666  		// Test basic request (no accept-encoding)
   667  		req, _ := NewRequest("GET", fmt.Sprintf("%s/?testnum=%d&expect_accept=%s", ts.URL, i, test.expectAccept), nil)
   668  		if test.accept != "" {
   669  			req.Header.Set("Accept-Encoding", test.accept)
   670  		}
   671  		res, err := DefaultTransport.RoundTrip(req)
   672  		var body []byte
   673  		if test.compressed {
   674  			var r *gzip.Reader
   675  			r, err = gzip.NewReader(res.Body)
   676  			if err != nil {
   677  				t.Errorf("%d. gzip NewReader: %v", i, err)
   678  				continue
   679  			}
   680  			body, err = ioutil.ReadAll(r)
   681  			res.Body.Close()
   682  		} else {
   683  			body, err = ioutil.ReadAll(res.Body)
   684  		}
   685  		if err != nil {
   686  			t.Errorf("%d. Error: %q", i, err)
   687  			continue
   688  		}
   689  		if g, e := string(body), responseBody; g != e {
   690  			t.Errorf("%d. body = %q; want %q", i, g, e)
   691  		}
   692  		if g, e := req.Header.Get("Accept-Encoding"), test.accept; g != e {
   693  			t.Errorf("%d. Accept-Encoding = %q; want %q (it was mutated, in violation of RoundTrip contract)", i, g, e)
   694  		}
   695  		if g, e := res.Header.Get("Content-Encoding"), test.accept; g != e {
   696  			t.Errorf("%d. Content-Encoding = %q; want %q", i, g, e)
   697  		}
   698  	}
   699  
   700  }
   701  
   702  func TestTransportGzip(t *testing.T) {
   703  	defer afterTest(t)
   704  	const testString = "The test string aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
   705  	const nRandBytes = 1024 * 1024
   706  	ts := httptest.NewServer(HandlerFunc(func(rw ResponseWriter, req *Request) {
   707  		if req.Method == "HEAD" {
   708  			if g := req.Header.Get("Accept-Encoding"); g != "" {
   709  				t.Errorf("HEAD request sent with Accept-Encoding of %q; want none", g)
   710  			}
   711  			return
   712  		}
   713  		if g, e := req.Header.Get("Accept-Encoding"), "gzip"; g != e {
   714  			t.Errorf("Accept-Encoding = %q, want %q", g, e)
   715  		}
   716  		rw.Header().Set("Content-Encoding", "gzip")
   717  
   718  		var w io.Writer = rw
   719  		var buf bytes.Buffer
   720  		if req.FormValue("chunked") == "0" {
   721  			w = &buf
   722  			defer io.Copy(rw, &buf)
   723  			defer func() {
   724  				rw.Header().Set("Content-Length", strconv.Itoa(buf.Len()))
   725  			}()
   726  		}
   727  		gz := gzip.NewWriter(w)
   728  		gz.Write([]byte(testString))
   729  		if req.FormValue("body") == "large" {
   730  			io.CopyN(gz, rand.Reader, nRandBytes)
   731  		}
   732  		gz.Close()
   733  	}))
   734  	defer ts.Close()
   735  
   736  	for _, chunked := range []string{"1", "0"} {
   737  		c := &Client{Transport: &Transport{}}
   738  
   739  		// First fetch something large, but only read some of it.
   740  		res, err := c.Get(ts.URL + "/?body=large&chunked=" + chunked)
   741  		if err != nil {
   742  			t.Fatalf("large get: %v", err)
   743  		}
   744  		buf := make([]byte, len(testString))
   745  		n, err := io.ReadFull(res.Body, buf)
   746  		if err != nil {
   747  			t.Fatalf("partial read of large response: size=%d, %v", n, err)
   748  		}
   749  		if e, g := testString, string(buf); e != g {
   750  			t.Errorf("partial read got %q, expected %q", g, e)
   751  		}
   752  		res.Body.Close()
   753  		// Read on the body, even though it's closed
   754  		n, err = res.Body.Read(buf)
   755  		if n != 0 || err == nil {
   756  			t.Errorf("expected error post-closed large Read; got = %d, %v", n, err)
   757  		}
   758  
   759  		// Then something small.
   760  		res, err = c.Get(ts.URL + "/?chunked=" + chunked)
   761  		if err != nil {
   762  			t.Fatal(err)
   763  		}
   764  		body, err := ioutil.ReadAll(res.Body)
   765  		if err != nil {
   766  			t.Fatal(err)
   767  		}
   768  		if g, e := string(body), testString; g != e {
   769  			t.Fatalf("body = %q; want %q", g, e)
   770  		}
   771  		if g, e := res.Header.Get("Content-Encoding"), ""; g != e {
   772  			t.Fatalf("Content-Encoding = %q; want %q", g, e)
   773  		}
   774  
   775  		// Read on the body after it's been fully read:
   776  		n, err = res.Body.Read(buf)
   777  		if n != 0 || err == nil {
   778  			t.Errorf("expected Read error after exhausted reads; got %d, %v", n, err)
   779  		}
   780  		res.Body.Close()
   781  		n, err = res.Body.Read(buf)
   782  		if n != 0 || err == nil {
   783  			t.Errorf("expected Read error after Close; got %d, %v", n, err)
   784  		}
   785  	}
   786  
   787  	// And a HEAD request too, because they're always weird.
   788  	c := &Client{Transport: &Transport{}}
   789  	res, err := c.Head(ts.URL)
   790  	if err != nil {
   791  		t.Fatalf("Head: %v", err)
   792  	}
   793  	if res.StatusCode != 200 {
   794  		t.Errorf("Head status=%d; want=200", res.StatusCode)
   795  	}
   796  }
   797  
   798  // If a request has Expect:100-continue header, the request blocks sending body until the first response.
   799  // Premature consumption of the request body should not be occurred.
   800  func TestTransportExpect100Continue(t *testing.T) {
   801  	defer afterTest(t)
   802  
   803  	ts := httptest.NewServer(HandlerFunc(func(rw ResponseWriter, req *Request) {
   804  		switch req.URL.Path {
   805  		case "/100":
   806  			// This endpoint implicitly responds 100 Continue and reads body.
   807  			if _, err := io.Copy(ioutil.Discard, req.Body); err != nil {
   808  				t.Error("Failed to read Body", err)
   809  			}
   810  			rw.WriteHeader(StatusOK)
   811  		case "/200":
   812  			// Go 1.5 adds Connection: close header if the client expect
   813  			// continue but not entire request body is consumed.
   814  			rw.WriteHeader(StatusOK)
   815  		case "/500":
   816  			rw.WriteHeader(StatusInternalServerError)
   817  		case "/keepalive":
   818  			// This hijacked endpoint responds error without Connection:close.
   819  			_, bufrw, err := rw.(Hijacker).Hijack()
   820  			if err != nil {
   821  				log.Fatal(err)
   822  			}
   823  			bufrw.WriteString("HTTP/1.1 500 Internal Server Error\r\n")
   824  			bufrw.WriteString("Content-Length: 0\r\n\r\n")
   825  			bufrw.Flush()
   826  		case "/timeout":
   827  			// This endpoint tries to read body without 100 (Continue) response.
   828  			// After ExpectContinueTimeout, the reading will be started.
   829  			conn, bufrw, err := rw.(Hijacker).Hijack()
   830  			if err != nil {
   831  				log.Fatal(err)
   832  			}
   833  			if _, err := io.CopyN(ioutil.Discard, bufrw, req.ContentLength); err != nil {
   834  				t.Error("Failed to read Body", err)
   835  			}
   836  			bufrw.WriteString("HTTP/1.1 200 OK\r\n\r\n")
   837  			bufrw.Flush()
   838  			conn.Close()
   839  		}
   840  
   841  	}))
   842  	defer ts.Close()
   843  
   844  	tests := []struct {
   845  		path   string
   846  		body   []byte
   847  		sent   int
   848  		status int
   849  	}{
   850  		{path: "/100", body: []byte("hello"), sent: 5, status: 200},       // Got 100 followed by 200, entire body is sent.
   851  		{path: "/200", body: []byte("hello"), sent: 0, status: 200},       // Got 200 without 100. body isn't sent.
   852  		{path: "/500", body: []byte("hello"), sent: 0, status: 500},       // Got 500 without 100. body isn't sent.
   853  		{path: "/keepalive", body: []byte("hello"), sent: 0, status: 500}, // Althogh without Connection:close, body isn't sent.
   854  		{path: "/timeout", body: []byte("hello"), sent: 5, status: 200},   // Timeout exceeded and entire body is sent.
   855  	}
   856  
   857  	for i, v := range tests {
   858  		tr := &Transport{ExpectContinueTimeout: 2 * time.Second}
   859  		defer tr.CloseIdleConnections()
   860  		c := &Client{Transport: tr}
   861  
   862  		body := bytes.NewReader(v.body)
   863  		req, err := NewRequest("PUT", ts.URL+v.path, body)
   864  		if err != nil {
   865  			t.Fatal(err)
   866  		}
   867  		req.Header.Set("Expect", "100-continue")
   868  		req.ContentLength = int64(len(v.body))
   869  
   870  		resp, err := c.Do(req)
   871  		if err != nil {
   872  			t.Fatal(err)
   873  		}
   874  		resp.Body.Close()
   875  
   876  		sent := len(v.body) - body.Len()
   877  		if v.status != resp.StatusCode {
   878  			t.Errorf("test %d: status code should be %d but got %d. (%s)", i, v.status, resp.StatusCode, v.path)
   879  		}
   880  		if v.sent != sent {
   881  			t.Errorf("test %d: sent body should be %d but sent %d. (%s)", i, v.sent, sent, v.path)
   882  		}
   883  	}
   884  }
   885  
   886  func TestTransportProxy(t *testing.T) {
   887  	defer afterTest(t)
   888  	ch := make(chan string, 1)
   889  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   890  		ch <- "real server"
   891  	}))
   892  	defer ts.Close()
   893  	proxy := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   894  		ch <- "proxy for " + r.URL.String()
   895  	}))
   896  	defer proxy.Close()
   897  
   898  	pu, err := url.Parse(proxy.URL)
   899  	if err != nil {
   900  		t.Fatal(err)
   901  	}
   902  	c := &Client{Transport: &Transport{Proxy: ProxyURL(pu)}}
   903  	c.Head(ts.URL)
   904  	got := <-ch
   905  	want := "proxy for " + ts.URL + "/"
   906  	if got != want {
   907  		t.Errorf("want %q, got %q", want, got)
   908  	}
   909  }
   910  
   911  // TestTransportGzipRecursive sends a gzip quine and checks that the
   912  // client gets the same value back. This is more cute than anything,
   913  // but checks that we don't recurse forever, and checks that
   914  // Content-Encoding is removed.
   915  func TestTransportGzipRecursive(t *testing.T) {
   916  	defer afterTest(t)
   917  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   918  		w.Header().Set("Content-Encoding", "gzip")
   919  		w.Write(rgz)
   920  	}))
   921  	defer ts.Close()
   922  
   923  	c := &Client{Transport: &Transport{}}
   924  	res, err := c.Get(ts.URL)
   925  	if err != nil {
   926  		t.Fatal(err)
   927  	}
   928  	body, err := ioutil.ReadAll(res.Body)
   929  	if err != nil {
   930  		t.Fatal(err)
   931  	}
   932  	if !bytes.Equal(body, rgz) {
   933  		t.Fatalf("Incorrect result from recursive gz:\nhave=%x\nwant=%x",
   934  			body, rgz)
   935  	}
   936  	if g, e := res.Header.Get("Content-Encoding"), ""; g != e {
   937  		t.Fatalf("Content-Encoding = %q; want %q", g, e)
   938  	}
   939  }
   940  
   941  // golang.org/issue/7750: request fails when server replies with
   942  // a short gzip body
   943  func TestTransportGzipShort(t *testing.T) {
   944  	defer afterTest(t)
   945  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   946  		w.Header().Set("Content-Encoding", "gzip")
   947  		w.Write([]byte{0x1f, 0x8b})
   948  	}))
   949  	defer ts.Close()
   950  
   951  	tr := &Transport{}
   952  	defer tr.CloseIdleConnections()
   953  	c := &Client{Transport: tr}
   954  	res, err := c.Get(ts.URL)
   955  	if err != nil {
   956  		t.Fatal(err)
   957  	}
   958  	defer res.Body.Close()
   959  	_, err = ioutil.ReadAll(res.Body)
   960  	if err == nil {
   961  		t.Fatal("Expect an error from reading a body.")
   962  	}
   963  	if err != io.ErrUnexpectedEOF {
   964  		t.Errorf("ReadAll error = %v; want io.ErrUnexpectedEOF", err)
   965  	}
   966  }
   967  
   968  // tests that persistent goroutine connections shut down when no longer desired.
   969  func TestTransportPersistConnLeak(t *testing.T) {
   970  	defer afterTest(t)
   971  	gotReqCh := make(chan bool)
   972  	unblockCh := make(chan bool)
   973  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
   974  		gotReqCh <- true
   975  		<-unblockCh
   976  		w.Header().Set("Content-Length", "0")
   977  		w.WriteHeader(204)
   978  	}))
   979  	defer ts.Close()
   980  
   981  	tr := &Transport{}
   982  	c := &Client{Transport: tr}
   983  
   984  	n0 := runtime.NumGoroutine()
   985  
   986  	const numReq = 25
   987  	didReqCh := make(chan bool)
   988  	for i := 0; i < numReq; i++ {
   989  		go func() {
   990  			res, err := c.Get(ts.URL)
   991  			didReqCh <- true
   992  			if err != nil {
   993  				t.Errorf("client fetch error: %v", err)
   994  				return
   995  			}
   996  			res.Body.Close()
   997  		}()
   998  	}
   999  
  1000  	// Wait for all goroutines to be stuck in the Handler.
  1001  	for i := 0; i < numReq; i++ {
  1002  		<-gotReqCh
  1003  	}
  1004  
  1005  	nhigh := runtime.NumGoroutine()
  1006  
  1007  	// Tell all handlers to unblock and reply.
  1008  	for i := 0; i < numReq; i++ {
  1009  		unblockCh <- true
  1010  	}
  1011  
  1012  	// Wait for all HTTP clients to be done.
  1013  	for i := 0; i < numReq; i++ {
  1014  		<-didReqCh
  1015  	}
  1016  
  1017  	tr.CloseIdleConnections()
  1018  	time.Sleep(100 * time.Millisecond)
  1019  	runtime.GC()
  1020  	runtime.GC() // even more.
  1021  	nfinal := runtime.NumGoroutine()
  1022  
  1023  	growth := nfinal - n0
  1024  
  1025  	// We expect 0 or 1 extra goroutine, empirically.  Allow up to 5.
  1026  	// Previously we were leaking one per numReq.
  1027  	if int(growth) > 5 {
  1028  		t.Logf("goroutine growth: %d -> %d -> %d (delta: %d)", n0, nhigh, nfinal, growth)
  1029  		t.Error("too many new goroutines")
  1030  	}
  1031  }
  1032  
  1033  // golang.org/issue/4531: Transport leaks goroutines when
  1034  // request.ContentLength is explicitly short
  1035  func TestTransportPersistConnLeakShortBody(t *testing.T) {
  1036  	defer afterTest(t)
  1037  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1038  	}))
  1039  	defer ts.Close()
  1040  
  1041  	tr := &Transport{}
  1042  	c := &Client{Transport: tr}
  1043  
  1044  	n0 := runtime.NumGoroutine()
  1045  	body := []byte("Hello")
  1046  	for i := 0; i < 20; i++ {
  1047  		req, err := NewRequest("POST", ts.URL, bytes.NewReader(body))
  1048  		if err != nil {
  1049  			t.Fatal(err)
  1050  		}
  1051  		req.ContentLength = int64(len(body) - 2) // explicitly short
  1052  		_, err = c.Do(req)
  1053  		if err == nil {
  1054  			t.Fatal("Expect an error from writing too long of a body.")
  1055  		}
  1056  	}
  1057  	nhigh := runtime.NumGoroutine()
  1058  	tr.CloseIdleConnections()
  1059  	time.Sleep(400 * time.Millisecond)
  1060  	runtime.GC()
  1061  	nfinal := runtime.NumGoroutine()
  1062  
  1063  	growth := nfinal - n0
  1064  
  1065  	// We expect 0 or 1 extra goroutine, empirically.  Allow up to 5.
  1066  	// Previously we were leaking one per numReq.
  1067  	t.Logf("goroutine growth: %d -> %d -> %d (delta: %d)", n0, nhigh, nfinal, growth)
  1068  	if int(growth) > 5 {
  1069  		t.Error("too many new goroutines")
  1070  	}
  1071  }
  1072  
  1073  // This used to crash; https://golang.org/issue/3266
  1074  func TestTransportIdleConnCrash(t *testing.T) {
  1075  	defer afterTest(t)
  1076  	tr := &Transport{}
  1077  	c := &Client{Transport: tr}
  1078  
  1079  	unblockCh := make(chan bool, 1)
  1080  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1081  		<-unblockCh
  1082  		tr.CloseIdleConnections()
  1083  	}))
  1084  	defer ts.Close()
  1085  
  1086  	didreq := make(chan bool)
  1087  	go func() {
  1088  		res, err := c.Get(ts.URL)
  1089  		if err != nil {
  1090  			t.Error(err)
  1091  		} else {
  1092  			res.Body.Close() // returns idle conn
  1093  		}
  1094  		didreq <- true
  1095  	}()
  1096  	unblockCh <- true
  1097  	<-didreq
  1098  }
  1099  
  1100  // Test that the transport doesn't close the TCP connection early,
  1101  // before the response body has been read.  This was a regression
  1102  // which sadly lacked a triggering test.  The large response body made
  1103  // the old race easier to trigger.
  1104  func TestIssue3644(t *testing.T) {
  1105  	defer afterTest(t)
  1106  	const numFoos = 5000
  1107  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1108  		w.Header().Set("Connection", "close")
  1109  		for i := 0; i < numFoos; i++ {
  1110  			w.Write([]byte("foo "))
  1111  		}
  1112  	}))
  1113  	defer ts.Close()
  1114  	tr := &Transport{}
  1115  	c := &Client{Transport: tr}
  1116  	res, err := c.Get(ts.URL)
  1117  	if err != nil {
  1118  		t.Fatal(err)
  1119  	}
  1120  	defer res.Body.Close()
  1121  	bs, err := ioutil.ReadAll(res.Body)
  1122  	if err != nil {
  1123  		t.Fatal(err)
  1124  	}
  1125  	if len(bs) != numFoos*len("foo ") {
  1126  		t.Errorf("unexpected response length")
  1127  	}
  1128  }
  1129  
  1130  // Test that a client receives a server's reply, even if the server doesn't read
  1131  // the entire request body.
  1132  func TestIssue3595(t *testing.T) {
  1133  	defer afterTest(t)
  1134  	const deniedMsg = "sorry, denied."
  1135  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1136  		Error(w, deniedMsg, StatusUnauthorized)
  1137  	}))
  1138  	defer ts.Close()
  1139  	tr := &Transport{}
  1140  	c := &Client{Transport: tr}
  1141  	res, err := c.Post(ts.URL, "application/octet-stream", neverEnding('a'))
  1142  	if err != nil {
  1143  		t.Errorf("Post: %v", err)
  1144  		return
  1145  	}
  1146  	got, err := ioutil.ReadAll(res.Body)
  1147  	if err != nil {
  1148  		t.Fatalf("Body ReadAll: %v", err)
  1149  	}
  1150  	if !strings.Contains(string(got), deniedMsg) {
  1151  		t.Errorf("Known bug: response %q does not contain %q", got, deniedMsg)
  1152  	}
  1153  }
  1154  
  1155  // From https://golang.org/issue/4454 ,
  1156  // "client fails to handle requests with no body and chunked encoding"
  1157  func TestChunkedNoContent(t *testing.T) {
  1158  	defer afterTest(t)
  1159  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1160  		w.WriteHeader(StatusNoContent)
  1161  	}))
  1162  	defer ts.Close()
  1163  
  1164  	for _, closeBody := range []bool{true, false} {
  1165  		c := &Client{Transport: &Transport{}}
  1166  		const n = 4
  1167  		for i := 1; i <= n; i++ {
  1168  			res, err := c.Get(ts.URL)
  1169  			if err != nil {
  1170  				t.Errorf("closingBody=%v, req %d/%d: %v", closeBody, i, n, err)
  1171  			} else {
  1172  				if closeBody {
  1173  					res.Body.Close()
  1174  				}
  1175  			}
  1176  		}
  1177  	}
  1178  }
  1179  
  1180  func TestTransportConcurrency(t *testing.T) {
  1181  	defer afterTest(t)
  1182  	maxProcs, numReqs := 16, 500
  1183  	if testing.Short() {
  1184  		maxProcs, numReqs = 4, 50
  1185  	}
  1186  	defer runtime.GOMAXPROCS(runtime.GOMAXPROCS(maxProcs))
  1187  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1188  		fmt.Fprintf(w, "%v", r.FormValue("echo"))
  1189  	}))
  1190  	defer ts.Close()
  1191  
  1192  	var wg sync.WaitGroup
  1193  	wg.Add(numReqs)
  1194  
  1195  	// Due to the Transport's "socket late binding" (see
  1196  	// idleConnCh in transport.go), the numReqs HTTP requests
  1197  	// below can finish with a dial still outstanding.  To keep
  1198  	// the leak checker happy, keep track of pending dials and
  1199  	// wait for them to finish (and be closed or returned to the
  1200  	// idle pool) before we close idle connections.
  1201  	SetPendingDialHooks(func() { wg.Add(1) }, wg.Done)
  1202  	defer SetPendingDialHooks(nil, nil)
  1203  
  1204  	tr := &Transport{}
  1205  	defer tr.CloseIdleConnections()
  1206  
  1207  	c := &Client{Transport: tr}
  1208  	reqs := make(chan string)
  1209  	defer close(reqs)
  1210  
  1211  	for i := 0; i < maxProcs*2; i++ {
  1212  		go func() {
  1213  			for req := range reqs {
  1214  				res, err := c.Get(ts.URL + "/?echo=" + req)
  1215  				if err != nil {
  1216  					t.Errorf("error on req %s: %v", req, err)
  1217  					wg.Done()
  1218  					continue
  1219  				}
  1220  				all, err := ioutil.ReadAll(res.Body)
  1221  				if err != nil {
  1222  					t.Errorf("read error on req %s: %v", req, err)
  1223  					wg.Done()
  1224  					continue
  1225  				}
  1226  				if string(all) != req {
  1227  					t.Errorf("body of req %s = %q; want %q", req, all, req)
  1228  				}
  1229  				res.Body.Close()
  1230  				wg.Done()
  1231  			}
  1232  		}()
  1233  	}
  1234  	for i := 0; i < numReqs; i++ {
  1235  		reqs <- fmt.Sprintf("request-%d", i)
  1236  	}
  1237  	wg.Wait()
  1238  }
  1239  
  1240  func TestIssue4191_InfiniteGetTimeout(t *testing.T) {
  1241  	if runtime.GOOS == "plan9" {
  1242  		t.Skip("skipping test; see https://golang.org/issue/7237")
  1243  	}
  1244  	defer afterTest(t)
  1245  	const debug = false
  1246  	mux := NewServeMux()
  1247  	mux.HandleFunc("/get", func(w ResponseWriter, r *Request) {
  1248  		io.Copy(w, neverEnding('a'))
  1249  	})
  1250  	ts := httptest.NewServer(mux)
  1251  	timeout := 100 * time.Millisecond
  1252  
  1253  	client := &Client{
  1254  		Transport: &Transport{
  1255  			Dial: func(n, addr string) (net.Conn, error) {
  1256  				conn, err := net.Dial(n, addr)
  1257  				if err != nil {
  1258  					return nil, err
  1259  				}
  1260  				conn.SetDeadline(time.Now().Add(timeout))
  1261  				if debug {
  1262  					conn = NewLoggingConn("client", conn)
  1263  				}
  1264  				return conn, nil
  1265  			},
  1266  			DisableKeepAlives: true,
  1267  		},
  1268  	}
  1269  
  1270  	getFailed := false
  1271  	nRuns := 5
  1272  	if testing.Short() {
  1273  		nRuns = 1
  1274  	}
  1275  	for i := 0; i < nRuns; i++ {
  1276  		if debug {
  1277  			println("run", i+1, "of", nRuns)
  1278  		}
  1279  		sres, err := client.Get(ts.URL + "/get")
  1280  		if err != nil {
  1281  			if !getFailed {
  1282  				// Make the timeout longer, once.
  1283  				getFailed = true
  1284  				t.Logf("increasing timeout")
  1285  				i--
  1286  				timeout *= 10
  1287  				continue
  1288  			}
  1289  			t.Errorf("Error issuing GET: %v", err)
  1290  			break
  1291  		}
  1292  		_, err = io.Copy(ioutil.Discard, sres.Body)
  1293  		if err == nil {
  1294  			t.Errorf("Unexpected successful copy")
  1295  			break
  1296  		}
  1297  	}
  1298  	if debug {
  1299  		println("tests complete; waiting for handlers to finish")
  1300  	}
  1301  	ts.Close()
  1302  }
  1303  
  1304  func TestIssue4191_InfiniteGetToPutTimeout(t *testing.T) {
  1305  	if runtime.GOOS == "plan9" {
  1306  		t.Skip("skipping test; see https://golang.org/issue/7237")
  1307  	}
  1308  	defer afterTest(t)
  1309  	const debug = false
  1310  	mux := NewServeMux()
  1311  	mux.HandleFunc("/get", func(w ResponseWriter, r *Request) {
  1312  		io.Copy(w, neverEnding('a'))
  1313  	})
  1314  	mux.HandleFunc("/put", func(w ResponseWriter, r *Request) {
  1315  		defer r.Body.Close()
  1316  		io.Copy(ioutil.Discard, r.Body)
  1317  	})
  1318  	ts := httptest.NewServer(mux)
  1319  	timeout := 100 * time.Millisecond
  1320  
  1321  	client := &Client{
  1322  		Transport: &Transport{
  1323  			Dial: func(n, addr string) (net.Conn, error) {
  1324  				conn, err := net.Dial(n, addr)
  1325  				if err != nil {
  1326  					return nil, err
  1327  				}
  1328  				conn.SetDeadline(time.Now().Add(timeout))
  1329  				if debug {
  1330  					conn = NewLoggingConn("client", conn)
  1331  				}
  1332  				return conn, nil
  1333  			},
  1334  			DisableKeepAlives: true,
  1335  		},
  1336  	}
  1337  
  1338  	getFailed := false
  1339  	nRuns := 5
  1340  	if testing.Short() {
  1341  		nRuns = 1
  1342  	}
  1343  	for i := 0; i < nRuns; i++ {
  1344  		if debug {
  1345  			println("run", i+1, "of", nRuns)
  1346  		}
  1347  		sres, err := client.Get(ts.URL + "/get")
  1348  		if err != nil {
  1349  			if !getFailed {
  1350  				// Make the timeout longer, once.
  1351  				getFailed = true
  1352  				t.Logf("increasing timeout")
  1353  				i--
  1354  				timeout *= 10
  1355  				continue
  1356  			}
  1357  			t.Errorf("Error issuing GET: %v", err)
  1358  			break
  1359  		}
  1360  		req, _ := NewRequest("PUT", ts.URL+"/put", sres.Body)
  1361  		_, err = client.Do(req)
  1362  		if err == nil {
  1363  			sres.Body.Close()
  1364  			t.Errorf("Unexpected successful PUT")
  1365  			break
  1366  		}
  1367  		sres.Body.Close()
  1368  	}
  1369  	if debug {
  1370  		println("tests complete; waiting for handlers to finish")
  1371  	}
  1372  	ts.Close()
  1373  }
  1374  
  1375  func TestTransportResponseHeaderTimeout(t *testing.T) {
  1376  	defer afterTest(t)
  1377  	if testing.Short() {
  1378  		t.Skip("skipping timeout test in -short mode")
  1379  	}
  1380  	inHandler := make(chan bool, 1)
  1381  	mux := NewServeMux()
  1382  	mux.HandleFunc("/fast", func(w ResponseWriter, r *Request) {
  1383  		inHandler <- true
  1384  	})
  1385  	mux.HandleFunc("/slow", func(w ResponseWriter, r *Request) {
  1386  		inHandler <- true
  1387  		time.Sleep(2 * time.Second)
  1388  	})
  1389  	ts := httptest.NewServer(mux)
  1390  	defer ts.Close()
  1391  
  1392  	tr := &Transport{
  1393  		ResponseHeaderTimeout: 500 * time.Millisecond,
  1394  	}
  1395  	defer tr.CloseIdleConnections()
  1396  	c := &Client{Transport: tr}
  1397  
  1398  	tests := []struct {
  1399  		path    string
  1400  		want    int
  1401  		wantErr string
  1402  	}{
  1403  		{path: "/fast", want: 200},
  1404  		{path: "/slow", wantErr: "timeout awaiting response headers"},
  1405  		{path: "/fast", want: 200},
  1406  	}
  1407  	for i, tt := range tests {
  1408  		res, err := c.Get(ts.URL + tt.path)
  1409  		select {
  1410  		case <-inHandler:
  1411  		case <-time.After(5 * time.Second):
  1412  			t.Errorf("never entered handler for test index %d, %s", i, tt.path)
  1413  			continue
  1414  		}
  1415  		if err != nil {
  1416  			uerr, ok := err.(*url.Error)
  1417  			if !ok {
  1418  				t.Errorf("error is not an url.Error; got: %#v", err)
  1419  				continue
  1420  			}
  1421  			nerr, ok := uerr.Err.(net.Error)
  1422  			if !ok {
  1423  				t.Errorf("error does not satisfy net.Error interface; got: %#v", err)
  1424  				continue
  1425  			}
  1426  			if !nerr.Timeout() {
  1427  				t.Errorf("want timeout error; got: %q", nerr)
  1428  				continue
  1429  			}
  1430  			if strings.Contains(err.Error(), tt.wantErr) {
  1431  				continue
  1432  			}
  1433  			t.Errorf("%d. unexpected error: %v", i, err)
  1434  			continue
  1435  		}
  1436  		if tt.wantErr != "" {
  1437  			t.Errorf("%d. no error. expected error: %v", i, tt.wantErr)
  1438  			continue
  1439  		}
  1440  		if res.StatusCode != tt.want {
  1441  			t.Errorf("%d for path %q status = %d; want %d", i, tt.path, res.StatusCode, tt.want)
  1442  		}
  1443  	}
  1444  }
  1445  
  1446  func TestTransportCancelRequest(t *testing.T) {
  1447  	defer afterTest(t)
  1448  	if testing.Short() {
  1449  		t.Skip("skipping test in -short mode")
  1450  	}
  1451  	unblockc := make(chan bool)
  1452  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1453  		fmt.Fprintf(w, "Hello")
  1454  		w.(Flusher).Flush() // send headers and some body
  1455  		<-unblockc
  1456  	}))
  1457  	defer ts.Close()
  1458  	defer close(unblockc)
  1459  
  1460  	tr := &Transport{}
  1461  	defer tr.CloseIdleConnections()
  1462  	c := &Client{Transport: tr}
  1463  
  1464  	req, _ := NewRequest("GET", ts.URL, nil)
  1465  	res, err := c.Do(req)
  1466  	if err != nil {
  1467  		t.Fatal(err)
  1468  	}
  1469  	go func() {
  1470  		time.Sleep(1 * time.Second)
  1471  		tr.CancelRequest(req)
  1472  	}()
  1473  	t0 := time.Now()
  1474  	body, err := ioutil.ReadAll(res.Body)
  1475  	d := time.Since(t0)
  1476  
  1477  	if err != ExportErrRequestCanceled {
  1478  		t.Errorf("Body.Read error = %v; want errRequestCanceled", err)
  1479  	}
  1480  	if string(body) != "Hello" {
  1481  		t.Errorf("Body = %q; want Hello", body)
  1482  	}
  1483  	if d < 500*time.Millisecond {
  1484  		t.Errorf("expected ~1 second delay; got %v", d)
  1485  	}
  1486  	// Verify no outstanding requests after readLoop/writeLoop
  1487  	// goroutines shut down.
  1488  	for tries := 5; tries > 0; tries-- {
  1489  		n := tr.NumPendingRequestsForTesting()
  1490  		if n == 0 {
  1491  			break
  1492  		}
  1493  		time.Sleep(100 * time.Millisecond)
  1494  		if tries == 1 {
  1495  			t.Errorf("pending requests = %d; want 0", n)
  1496  		}
  1497  	}
  1498  }
  1499  
  1500  func TestTransportCancelRequestInDial(t *testing.T) {
  1501  	defer afterTest(t)
  1502  	if testing.Short() {
  1503  		t.Skip("skipping test in -short mode")
  1504  	}
  1505  	var logbuf bytes.Buffer
  1506  	eventLog := log.New(&logbuf, "", 0)
  1507  
  1508  	unblockDial := make(chan bool)
  1509  	defer close(unblockDial)
  1510  
  1511  	inDial := make(chan bool)
  1512  	tr := &Transport{
  1513  		Dial: func(network, addr string) (net.Conn, error) {
  1514  			eventLog.Println("dial: blocking")
  1515  			inDial <- true
  1516  			<-unblockDial
  1517  			return nil, errors.New("nope")
  1518  		},
  1519  	}
  1520  	cl := &Client{Transport: tr}
  1521  	gotres := make(chan bool)
  1522  	req, _ := NewRequest("GET", "http://something.no-network.tld/", nil)
  1523  	go func() {
  1524  		_, err := cl.Do(req)
  1525  		eventLog.Printf("Get = %v", err)
  1526  		gotres <- true
  1527  	}()
  1528  
  1529  	select {
  1530  	case <-inDial:
  1531  	case <-time.After(5 * time.Second):
  1532  		t.Fatal("timeout; never saw blocking dial")
  1533  	}
  1534  
  1535  	eventLog.Printf("canceling")
  1536  	tr.CancelRequest(req)
  1537  	tr.CancelRequest(req) // used to panic on second call
  1538  
  1539  	select {
  1540  	case <-gotres:
  1541  	case <-time.After(5 * time.Second):
  1542  		panic("hang. events are: " + logbuf.String())
  1543  	}
  1544  
  1545  	got := logbuf.String()
  1546  	want := `dial: blocking
  1547  canceling
  1548  Get = Get http://something.no-network.tld/: net/http: request canceled while waiting for connection
  1549  `
  1550  	if got != want {
  1551  		t.Errorf("Got events:\n%s\nWant:\n%s", got, want)
  1552  	}
  1553  }
  1554  
  1555  func TestCancelRequestWithChannel(t *testing.T) {
  1556  	defer afterTest(t)
  1557  	if testing.Short() {
  1558  		t.Skip("skipping test in -short mode")
  1559  	}
  1560  	unblockc := make(chan bool)
  1561  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1562  		fmt.Fprintf(w, "Hello")
  1563  		w.(Flusher).Flush() // send headers and some body
  1564  		<-unblockc
  1565  	}))
  1566  	defer ts.Close()
  1567  	defer close(unblockc)
  1568  
  1569  	tr := &Transport{}
  1570  	defer tr.CloseIdleConnections()
  1571  	c := &Client{Transport: tr}
  1572  
  1573  	req, _ := NewRequest("GET", ts.URL, nil)
  1574  	ch := make(chan struct{})
  1575  	req.Cancel = ch
  1576  
  1577  	res, err := c.Do(req)
  1578  	if err != nil {
  1579  		t.Fatal(err)
  1580  	}
  1581  	go func() {
  1582  		time.Sleep(1 * time.Second)
  1583  		close(ch)
  1584  	}()
  1585  	t0 := time.Now()
  1586  	body, err := ioutil.ReadAll(res.Body)
  1587  	d := time.Since(t0)
  1588  
  1589  	if err != ExportErrRequestCanceled {
  1590  		t.Errorf("Body.Read error = %v; want errRequestCanceled", err)
  1591  	}
  1592  	if string(body) != "Hello" {
  1593  		t.Errorf("Body = %q; want Hello", body)
  1594  	}
  1595  	if d < 500*time.Millisecond {
  1596  		t.Errorf("expected ~1 second delay; got %v", d)
  1597  	}
  1598  	// Verify no outstanding requests after readLoop/writeLoop
  1599  	// goroutines shut down.
  1600  	for tries := 5; tries > 0; tries-- {
  1601  		n := tr.NumPendingRequestsForTesting()
  1602  		if n == 0 {
  1603  			break
  1604  		}
  1605  		time.Sleep(100 * time.Millisecond)
  1606  		if tries == 1 {
  1607  			t.Errorf("pending requests = %d; want 0", n)
  1608  		}
  1609  	}
  1610  }
  1611  
  1612  func TestCancelRequestWithChannelBeforeDo(t *testing.T) {
  1613  	defer afterTest(t)
  1614  	unblockc := make(chan bool)
  1615  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1616  		<-unblockc
  1617  	}))
  1618  	defer ts.Close()
  1619  	defer close(unblockc)
  1620  
  1621  	// Don't interfere with the next test on plan9.
  1622  	// Cf. https://golang.org/issues/11476
  1623  	if runtime.GOOS == "plan9" {
  1624  		defer time.Sleep(500 * time.Millisecond)
  1625  	}
  1626  
  1627  	tr := &Transport{}
  1628  	defer tr.CloseIdleConnections()
  1629  	c := &Client{Transport: tr}
  1630  
  1631  	req, _ := NewRequest("GET", ts.URL, nil)
  1632  	ch := make(chan struct{})
  1633  	req.Cancel = ch
  1634  	close(ch)
  1635  
  1636  	_, err := c.Do(req)
  1637  	if err == nil || !strings.Contains(err.Error(), "canceled") {
  1638  		t.Errorf("Do error = %v; want cancelation", err)
  1639  	}
  1640  }
  1641  
  1642  // Issue 11020. The returned error message should be errRequestCanceled
  1643  func TestTransportCancelBeforeResponseHeaders(t *testing.T) {
  1644  	t.Skip("Skipping flaky test; see Issue 11894")
  1645  	defer afterTest(t)
  1646  
  1647  	serverConnCh := make(chan net.Conn, 1)
  1648  	tr := &Transport{
  1649  		Dial: func(network, addr string) (net.Conn, error) {
  1650  			cc, sc := net.Pipe()
  1651  			serverConnCh <- sc
  1652  			return cc, nil
  1653  		},
  1654  	}
  1655  	defer tr.CloseIdleConnections()
  1656  	errc := make(chan error, 1)
  1657  	req, _ := NewRequest("GET", "http://example.com/", nil)
  1658  	go func() {
  1659  		_, err := tr.RoundTrip(req)
  1660  		errc <- err
  1661  	}()
  1662  
  1663  	sc := <-serverConnCh
  1664  	verb := make([]byte, 3)
  1665  	if _, err := io.ReadFull(sc, verb); err != nil {
  1666  		t.Errorf("Error reading HTTP verb from server: %v", err)
  1667  	}
  1668  	if string(verb) != "GET" {
  1669  		t.Errorf("server received %q; want GET", verb)
  1670  	}
  1671  	defer sc.Close()
  1672  
  1673  	tr.CancelRequest(req)
  1674  
  1675  	err := <-errc
  1676  	if err == nil {
  1677  		t.Fatalf("unexpected success from RoundTrip")
  1678  	}
  1679  	if err != ExportErrRequestCanceled {
  1680  		t.Errorf("RoundTrip error = %v; want ExportErrRequestCanceled", err)
  1681  	}
  1682  }
  1683  
  1684  // golang.org/issue/3672 -- Client can't close HTTP stream
  1685  // Calling Close on a Response.Body used to just read until EOF.
  1686  // Now it actually closes the TCP connection.
  1687  func TestTransportCloseResponseBody(t *testing.T) {
  1688  	defer afterTest(t)
  1689  	writeErr := make(chan error, 1)
  1690  	msg := []byte("young\n")
  1691  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  1692  		for {
  1693  			_, err := w.Write(msg)
  1694  			if err != nil {
  1695  				writeErr <- err
  1696  				return
  1697  			}
  1698  			w.(Flusher).Flush()
  1699  		}
  1700  	}))
  1701  	defer ts.Close()
  1702  
  1703  	tr := &Transport{}
  1704  	defer tr.CloseIdleConnections()
  1705  	c := &Client{Transport: tr}
  1706  
  1707  	req, _ := NewRequest("GET", ts.URL, nil)
  1708  	defer tr.CancelRequest(req)
  1709  
  1710  	res, err := c.Do(req)
  1711  	if err != nil {
  1712  		t.Fatal(err)
  1713  	}
  1714  
  1715  	const repeats = 3
  1716  	buf := make([]byte, len(msg)*repeats)
  1717  	want := bytes.Repeat(msg, repeats)
  1718  
  1719  	_, err = io.ReadFull(res.Body, buf)
  1720  	if err != nil {
  1721  		t.Fatal(err)
  1722  	}
  1723  	if !bytes.Equal(buf, want) {
  1724  		t.Fatalf("read %q; want %q", buf, want)
  1725  	}
  1726  	didClose := make(chan error, 1)
  1727  	go func() {
  1728  		didClose <- res.Body.Close()
  1729  	}()
  1730  	select {
  1731  	case err := <-didClose:
  1732  		if err != nil {
  1733  			t.Errorf("Close = %v", err)
  1734  		}
  1735  	case <-time.After(10 * time.Second):
  1736  		t.Fatal("too long waiting for close")
  1737  	}
  1738  	select {
  1739  	case err := <-writeErr:
  1740  		if err == nil {
  1741  			t.Errorf("expected non-nil write error")
  1742  		}
  1743  	case <-time.After(10 * time.Second):
  1744  		t.Fatal("too long waiting for write error")
  1745  	}
  1746  }
  1747  
  1748  type fooProto struct{}
  1749  
  1750  func (fooProto) RoundTrip(req *Request) (*Response, error) {
  1751  	res := &Response{
  1752  		Status:     "200 OK",
  1753  		StatusCode: 200,
  1754  		Header:     make(Header),
  1755  		Body:       ioutil.NopCloser(strings.NewReader("You wanted " + req.URL.String())),
  1756  	}
  1757  	return res, nil
  1758  }
  1759  
  1760  func TestTransportAltProto(t *testing.T) {
  1761  	defer afterTest(t)
  1762  	tr := &Transport{}
  1763  	c := &Client{Transport: tr}
  1764  	tr.RegisterProtocol("foo", fooProto{})
  1765  	res, err := c.Get("foo://bar.com/path")
  1766  	if err != nil {
  1767  		t.Fatal(err)
  1768  	}
  1769  	bodyb, err := ioutil.ReadAll(res.Body)
  1770  	if err != nil {
  1771  		t.Fatal(err)
  1772  	}
  1773  	body := string(bodyb)
  1774  	if e := "You wanted foo://bar.com/path"; body != e {
  1775  		t.Errorf("got response %q, want %q", body, e)
  1776  	}
  1777  }
  1778  
  1779  func TestTransportNoHost(t *testing.T) {
  1780  	defer afterTest(t)
  1781  	tr := &Transport{}
  1782  	_, err := tr.RoundTrip(&Request{
  1783  		Header: make(Header),
  1784  		URL: &url.URL{
  1785  			Scheme: "http",
  1786  		},
  1787  	})
  1788  	want := "http: no Host in request URL"
  1789  	if got := fmt.Sprint(err); got != want {
  1790  		t.Errorf("error = %v; want %q", err, want)
  1791  	}
  1792  }
  1793  
  1794  // Issue 13311
  1795  func TestTransportEmptyMethod(t *testing.T) {
  1796  	req, _ := NewRequest("GET", "http://foo.com/", nil)
  1797  	req.Method = ""                                 // docs say "For client requests an empty string means GET"
  1798  	got, err := httputil.DumpRequestOut(req, false) // DumpRequestOut uses Transport
  1799  	if err != nil {
  1800  		t.Fatal(err)
  1801  	}
  1802  	if !strings.Contains(string(got), "GET ") {
  1803  		t.Fatalf("expected substring 'GET '; got: %s", got)
  1804  	}
  1805  }
  1806  
  1807  func TestTransportSocketLateBinding(t *testing.T) {
  1808  	defer afterTest(t)
  1809  
  1810  	mux := NewServeMux()
  1811  	fooGate := make(chan bool, 1)
  1812  	mux.HandleFunc("/foo", func(w ResponseWriter, r *Request) {
  1813  		w.Header().Set("foo-ipport", r.RemoteAddr)
  1814  		w.(Flusher).Flush()
  1815  		<-fooGate
  1816  	})
  1817  	mux.HandleFunc("/bar", func(w ResponseWriter, r *Request) {
  1818  		w.Header().Set("bar-ipport", r.RemoteAddr)
  1819  	})
  1820  	ts := httptest.NewServer(mux)
  1821  	defer ts.Close()
  1822  
  1823  	dialGate := make(chan bool, 1)
  1824  	tr := &Transport{
  1825  		Dial: func(n, addr string) (net.Conn, error) {
  1826  			if <-dialGate {
  1827  				return net.Dial(n, addr)
  1828  			}
  1829  			return nil, errors.New("manually closed")
  1830  		},
  1831  		DisableKeepAlives: false,
  1832  	}
  1833  	defer tr.CloseIdleConnections()
  1834  	c := &Client{
  1835  		Transport: tr,
  1836  	}
  1837  
  1838  	dialGate <- true // only allow one dial
  1839  	fooRes, err := c.Get(ts.URL + "/foo")
  1840  	if err != nil {
  1841  		t.Fatal(err)
  1842  	}
  1843  	fooAddr := fooRes.Header.Get("foo-ipport")
  1844  	if fooAddr == "" {
  1845  		t.Fatal("No addr on /foo request")
  1846  	}
  1847  	time.AfterFunc(200*time.Millisecond, func() {
  1848  		// let the foo response finish so we can use its
  1849  		// connection for /bar
  1850  		fooGate <- true
  1851  		io.Copy(ioutil.Discard, fooRes.Body)
  1852  		fooRes.Body.Close()
  1853  	})
  1854  
  1855  	barRes, err := c.Get(ts.URL + "/bar")
  1856  	if err != nil {
  1857  		t.Fatal(err)
  1858  	}
  1859  	barAddr := barRes.Header.Get("bar-ipport")
  1860  	if barAddr != fooAddr {
  1861  		t.Fatalf("/foo came from conn %q; /bar came from %q instead", fooAddr, barAddr)
  1862  	}
  1863  	barRes.Body.Close()
  1864  	dialGate <- false
  1865  }
  1866  
  1867  // Issue 2184
  1868  func TestTransportReading100Continue(t *testing.T) {
  1869  	defer afterTest(t)
  1870  
  1871  	const numReqs = 5
  1872  	reqBody := func(n int) string { return fmt.Sprintf("request body %d", n) }
  1873  	reqID := func(n int) string { return fmt.Sprintf("REQ-ID-%d", n) }
  1874  
  1875  	send100Response := func(w *io.PipeWriter, r *io.PipeReader) {
  1876  		defer w.Close()
  1877  		defer r.Close()
  1878  		br := bufio.NewReader(r)
  1879  		n := 0
  1880  		for {
  1881  			n++
  1882  			req, err := ReadRequest(br)
  1883  			if err == io.EOF {
  1884  				return
  1885  			}
  1886  			if err != nil {
  1887  				t.Error(err)
  1888  				return
  1889  			}
  1890  			slurp, err := ioutil.ReadAll(req.Body)
  1891  			if err != nil {
  1892  				t.Errorf("Server request body slurp: %v", err)
  1893  				return
  1894  			}
  1895  			id := req.Header.Get("Request-Id")
  1896  			resCode := req.Header.Get("X-Want-Response-Code")
  1897  			if resCode == "" {
  1898  				resCode = "100 Continue"
  1899  				if string(slurp) != reqBody(n) {
  1900  					t.Errorf("Server got %q, %v; want %q", slurp, err, reqBody(n))
  1901  				}
  1902  			}
  1903  			body := fmt.Sprintf("Response number %d", n)
  1904  			v := []byte(strings.Replace(fmt.Sprintf(`HTTP/1.1 %s
  1905  Date: Thu, 28 Feb 2013 17:55:41 GMT
  1906  
  1907  HTTP/1.1 200 OK
  1908  Content-Type: text/html
  1909  Echo-Request-Id: %s
  1910  Content-Length: %d
  1911  
  1912  %s`, resCode, id, len(body), body), "\n", "\r\n", -1))
  1913  			w.Write(v)
  1914  			if id == reqID(numReqs) {
  1915  				return
  1916  			}
  1917  		}
  1918  
  1919  	}
  1920  
  1921  	tr := &Transport{
  1922  		Dial: func(n, addr string) (net.Conn, error) {
  1923  			sr, sw := io.Pipe() // server read/write
  1924  			cr, cw := io.Pipe() // client read/write
  1925  			conn := &rwTestConn{
  1926  				Reader: cr,
  1927  				Writer: sw,
  1928  				closeFunc: func() error {
  1929  					sw.Close()
  1930  					cw.Close()
  1931  					return nil
  1932  				},
  1933  			}
  1934  			go send100Response(cw, sr)
  1935  			return conn, nil
  1936  		},
  1937  		DisableKeepAlives: false,
  1938  	}
  1939  	defer tr.CloseIdleConnections()
  1940  	c := &Client{Transport: tr}
  1941  
  1942  	testResponse := func(req *Request, name string, wantCode int) {
  1943  		res, err := c.Do(req)
  1944  		if err != nil {
  1945  			t.Fatalf("%s: Do: %v", name, err)
  1946  		}
  1947  		if res.StatusCode != wantCode {
  1948  			t.Fatalf("%s: Response Statuscode=%d; want %d", name, res.StatusCode, wantCode)
  1949  		}
  1950  		if id, idBack := req.Header.Get("Request-Id"), res.Header.Get("Echo-Request-Id"); id != "" && id != idBack {
  1951  			t.Errorf("%s: response id %q != request id %q", name, idBack, id)
  1952  		}
  1953  		_, err = ioutil.ReadAll(res.Body)
  1954  		if err != nil {
  1955  			t.Fatalf("%s: Slurp error: %v", name, err)
  1956  		}
  1957  	}
  1958  
  1959  	// Few 100 responses, making sure we're not off-by-one.
  1960  	for i := 1; i <= numReqs; i++ {
  1961  		req, _ := NewRequest("POST", "http://dummy.tld/", strings.NewReader(reqBody(i)))
  1962  		req.Header.Set("Request-Id", reqID(i))
  1963  		testResponse(req, fmt.Sprintf("100, %d/%d", i, numReqs), 200)
  1964  	}
  1965  
  1966  	// And some other informational 1xx but non-100 responses, to test
  1967  	// we return them but don't re-use the connection.
  1968  	for i := 1; i <= numReqs; i++ {
  1969  		req, _ := NewRequest("POST", "http://other.tld/", strings.NewReader(reqBody(i)))
  1970  		req.Header.Set("X-Want-Response-Code", "123 Sesame Street")
  1971  		testResponse(req, fmt.Sprintf("123, %d/%d", i, numReqs), 123)
  1972  	}
  1973  }
  1974  
  1975  type proxyFromEnvTest struct {
  1976  	req string // URL to fetch; blank means "http://example.com"
  1977  
  1978  	env      string // HTTP_PROXY
  1979  	httpsenv string // HTTPS_PROXY
  1980  	noenv    string // NO_RPXY
  1981  
  1982  	want    string
  1983  	wanterr error
  1984  }
  1985  
  1986  func (t proxyFromEnvTest) String() string {
  1987  	var buf bytes.Buffer
  1988  	space := func() {
  1989  		if buf.Len() > 0 {
  1990  			buf.WriteByte(' ')
  1991  		}
  1992  	}
  1993  	if t.env != "" {
  1994  		fmt.Fprintf(&buf, "http_proxy=%q", t.env)
  1995  	}
  1996  	if t.httpsenv != "" {
  1997  		space()
  1998  		fmt.Fprintf(&buf, "https_proxy=%q", t.httpsenv)
  1999  	}
  2000  	if t.noenv != "" {
  2001  		space()
  2002  		fmt.Fprintf(&buf, "no_proxy=%q", t.noenv)
  2003  	}
  2004  	req := "http://example.com"
  2005  	if t.req != "" {
  2006  		req = t.req
  2007  	}
  2008  	space()
  2009  	fmt.Fprintf(&buf, "req=%q", req)
  2010  	return strings.TrimSpace(buf.String())
  2011  }
  2012  
  2013  var proxyFromEnvTests = []proxyFromEnvTest{
  2014  	{env: "127.0.0.1:8080", want: "http://127.0.0.1:8080"},
  2015  	{env: "cache.corp.example.com:1234", want: "http://cache.corp.example.com:1234"},
  2016  	{env: "cache.corp.example.com", want: "http://cache.corp.example.com"},
  2017  	{env: "https://cache.corp.example.com", want: "https://cache.corp.example.com"},
  2018  	{env: "http://127.0.0.1:8080", want: "http://127.0.0.1:8080"},
  2019  	{env: "https://127.0.0.1:8080", want: "https://127.0.0.1:8080"},
  2020  
  2021  	// Don't use secure for http
  2022  	{req: "http://insecure.tld/", env: "http.proxy.tld", httpsenv: "secure.proxy.tld", want: "http://http.proxy.tld"},
  2023  	// Use secure for https.
  2024  	{req: "https://secure.tld/", env: "http.proxy.tld", httpsenv: "secure.proxy.tld", want: "http://secure.proxy.tld"},
  2025  	{req: "https://secure.tld/", env: "http.proxy.tld", httpsenv: "https://secure.proxy.tld", want: "https://secure.proxy.tld"},
  2026  
  2027  	{want: "<nil>"},
  2028  
  2029  	{noenv: "example.com", req: "http://example.com/", env: "proxy", want: "<nil>"},
  2030  	{noenv: ".example.com", req: "http://example.com/", env: "proxy", want: "<nil>"},
  2031  	{noenv: "ample.com", req: "http://example.com/", env: "proxy", want: "http://proxy"},
  2032  	{noenv: "example.com", req: "http://foo.example.com/", env: "proxy", want: "<nil>"},
  2033  	{noenv: ".foo.com", req: "http://example.com/", env: "proxy", want: "http://proxy"},
  2034  }
  2035  
  2036  func TestProxyFromEnvironment(t *testing.T) {
  2037  	ResetProxyEnv()
  2038  	for _, tt := range proxyFromEnvTests {
  2039  		os.Setenv("HTTP_PROXY", tt.env)
  2040  		os.Setenv("HTTPS_PROXY", tt.httpsenv)
  2041  		os.Setenv("NO_PROXY", tt.noenv)
  2042  		ResetCachedEnvironment()
  2043  		reqURL := tt.req
  2044  		if reqURL == "" {
  2045  			reqURL = "http://example.com"
  2046  		}
  2047  		req, _ := NewRequest("GET", reqURL, nil)
  2048  		url, err := ProxyFromEnvironment(req)
  2049  		if g, e := fmt.Sprintf("%v", err), fmt.Sprintf("%v", tt.wanterr); g != e {
  2050  			t.Errorf("%v: got error = %q, want %q", tt, g, e)
  2051  			continue
  2052  		}
  2053  		if got := fmt.Sprintf("%s", url); got != tt.want {
  2054  			t.Errorf("%v: got URL = %q, want %q", tt, url, tt.want)
  2055  		}
  2056  	}
  2057  }
  2058  
  2059  func TestIdleConnChannelLeak(t *testing.T) {
  2060  	var mu sync.Mutex
  2061  	var n int
  2062  
  2063  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2064  		mu.Lock()
  2065  		n++
  2066  		mu.Unlock()
  2067  	}))
  2068  	defer ts.Close()
  2069  
  2070  	const nReqs = 5
  2071  	didRead := make(chan bool, nReqs)
  2072  	SetReadLoopBeforeNextReadHook(func() { didRead <- true })
  2073  	defer SetReadLoopBeforeNextReadHook(nil)
  2074  
  2075  	tr := &Transport{
  2076  		Dial: func(netw, addr string) (net.Conn, error) {
  2077  			return net.Dial(netw, ts.Listener.Addr().String())
  2078  		},
  2079  	}
  2080  	defer tr.CloseIdleConnections()
  2081  
  2082  	c := &Client{Transport: tr}
  2083  
  2084  	// First, without keep-alives.
  2085  	for _, disableKeep := range []bool{true, false} {
  2086  		tr.DisableKeepAlives = disableKeep
  2087  		for i := 0; i < nReqs; i++ {
  2088  			_, err := c.Get(fmt.Sprintf("http://foo-host-%d.tld/", i))
  2089  			if err != nil {
  2090  				t.Fatal(err)
  2091  			}
  2092  			// Note: no res.Body.Close is needed here, since the
  2093  			// response Content-Length is zero. Perhaps the test
  2094  			// should be more explicit and use a HEAD, but tests
  2095  			// elsewhere guarantee that zero byte responses generate
  2096  			// a "Content-Length: 0" instead of chunking.
  2097  		}
  2098  
  2099  		// At this point, each of the 5 Transport.readLoop goroutines
  2100  		// are scheduling noting that there are no response bodies (see
  2101  		// earlier comment), and are then calling putIdleConn, which
  2102  		// decrements this count. Usually that happens quickly, which is
  2103  		// why this test has seemed to work for ages. But it's still
  2104  		// racey: we have wait for them to finish first. See Issue 10427
  2105  		for i := 0; i < nReqs; i++ {
  2106  			<-didRead
  2107  		}
  2108  
  2109  		if got := tr.IdleConnChMapSizeForTesting(); got != 0 {
  2110  			t.Fatalf("ForDisableKeepAlives = %v, map size = %d; want 0", disableKeep, got)
  2111  		}
  2112  	}
  2113  }
  2114  
  2115  // Verify the status quo: that the Client.Post function coerces its
  2116  // body into a ReadCloser if it's a Closer, and that the Transport
  2117  // then closes it.
  2118  func TestTransportClosesRequestBody(t *testing.T) {
  2119  	defer afterTest(t)
  2120  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2121  		io.Copy(ioutil.Discard, r.Body)
  2122  	}))
  2123  	defer ts.Close()
  2124  
  2125  	tr := &Transport{}
  2126  	defer tr.CloseIdleConnections()
  2127  	cl := &Client{Transport: tr}
  2128  
  2129  	closes := 0
  2130  
  2131  	res, err := cl.Post(ts.URL, "text/plain", countCloseReader{&closes, strings.NewReader("hello")})
  2132  	if err != nil {
  2133  		t.Fatal(err)
  2134  	}
  2135  	res.Body.Close()
  2136  	if closes != 1 {
  2137  		t.Errorf("closes = %d; want 1", closes)
  2138  	}
  2139  }
  2140  
  2141  func TestTransportTLSHandshakeTimeout(t *testing.T) {
  2142  	defer afterTest(t)
  2143  	if testing.Short() {
  2144  		t.Skip("skipping in short mode")
  2145  	}
  2146  	ln := newLocalListener(t)
  2147  	defer ln.Close()
  2148  	testdonec := make(chan struct{})
  2149  	defer close(testdonec)
  2150  
  2151  	go func() {
  2152  		c, err := ln.Accept()
  2153  		if err != nil {
  2154  			t.Error(err)
  2155  			return
  2156  		}
  2157  		<-testdonec
  2158  		c.Close()
  2159  	}()
  2160  
  2161  	getdonec := make(chan struct{})
  2162  	go func() {
  2163  		defer close(getdonec)
  2164  		tr := &Transport{
  2165  			Dial: func(_, _ string) (net.Conn, error) {
  2166  				return net.Dial("tcp", ln.Addr().String())
  2167  			},
  2168  			TLSHandshakeTimeout: 250 * time.Millisecond,
  2169  		}
  2170  		cl := &Client{Transport: tr}
  2171  		_, err := cl.Get("https://dummy.tld/")
  2172  		if err == nil {
  2173  			t.Error("expected error")
  2174  			return
  2175  		}
  2176  		ue, ok := err.(*url.Error)
  2177  		if !ok {
  2178  			t.Errorf("expected url.Error; got %#v", err)
  2179  			return
  2180  		}
  2181  		ne, ok := ue.Err.(net.Error)
  2182  		if !ok {
  2183  			t.Errorf("expected net.Error; got %#v", err)
  2184  			return
  2185  		}
  2186  		if !ne.Timeout() {
  2187  			t.Errorf("expected timeout error; got %v", err)
  2188  		}
  2189  		if !strings.Contains(err.Error(), "handshake timeout") {
  2190  			t.Errorf("expected 'handshake timeout' in error; got %v", err)
  2191  		}
  2192  	}()
  2193  	select {
  2194  	case <-getdonec:
  2195  	case <-time.After(5 * time.Second):
  2196  		t.Error("test timeout; TLS handshake hung?")
  2197  	}
  2198  }
  2199  
  2200  // Trying to repro golang.org/issue/3514
  2201  func TestTLSServerClosesConnection(t *testing.T) {
  2202  	defer afterTest(t)
  2203  	if runtime.GOOS == "windows" {
  2204  		t.Skip("skipping flaky test on Windows; golang.org/issue/7634")
  2205  	}
  2206  	closedc := make(chan bool, 1)
  2207  	ts := httptest.NewTLSServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2208  		if strings.Contains(r.URL.Path, "/keep-alive-then-die") {
  2209  			conn, _, _ := w.(Hijacker).Hijack()
  2210  			conn.Write([]byte("HTTP/1.1 200 OK\r\nContent-Length: 3\r\n\r\nfoo"))
  2211  			conn.Close()
  2212  			closedc <- true
  2213  			return
  2214  		}
  2215  		fmt.Fprintf(w, "hello")
  2216  	}))
  2217  	defer ts.Close()
  2218  	tr := &Transport{
  2219  		TLSClientConfig: &tls.Config{
  2220  			InsecureSkipVerify: true,
  2221  		},
  2222  	}
  2223  	defer tr.CloseIdleConnections()
  2224  	client := &Client{Transport: tr}
  2225  
  2226  	var nSuccess = 0
  2227  	var errs []error
  2228  	const trials = 20
  2229  	for i := 0; i < trials; i++ {
  2230  		tr.CloseIdleConnections()
  2231  		res, err := client.Get(ts.URL + "/keep-alive-then-die")
  2232  		if err != nil {
  2233  			t.Fatal(err)
  2234  		}
  2235  		<-closedc
  2236  		slurp, err := ioutil.ReadAll(res.Body)
  2237  		if err != nil {
  2238  			t.Fatal(err)
  2239  		}
  2240  		if string(slurp) != "foo" {
  2241  			t.Errorf("Got %q, want foo", slurp)
  2242  		}
  2243  
  2244  		// Now try again and see if we successfully
  2245  		// pick a new connection.
  2246  		res, err = client.Get(ts.URL + "/")
  2247  		if err != nil {
  2248  			errs = append(errs, err)
  2249  			continue
  2250  		}
  2251  		slurp, err = ioutil.ReadAll(res.Body)
  2252  		if err != nil {
  2253  			errs = append(errs, err)
  2254  			continue
  2255  		}
  2256  		nSuccess++
  2257  	}
  2258  	if nSuccess > 0 {
  2259  		t.Logf("successes = %d of %d", nSuccess, trials)
  2260  	} else {
  2261  		t.Errorf("All runs failed:")
  2262  	}
  2263  	for _, err := range errs {
  2264  		t.Logf("  err: %v", err)
  2265  	}
  2266  }
  2267  
  2268  // byteFromChanReader is an io.Reader that reads a single byte at a
  2269  // time from the channel.  When the channel is closed, the reader
  2270  // returns io.EOF.
  2271  type byteFromChanReader chan byte
  2272  
  2273  func (c byteFromChanReader) Read(p []byte) (n int, err error) {
  2274  	if len(p) == 0 {
  2275  		return
  2276  	}
  2277  	b, ok := <-c
  2278  	if !ok {
  2279  		return 0, io.EOF
  2280  	}
  2281  	p[0] = b
  2282  	return 1, nil
  2283  }
  2284  
  2285  // Verifies that the Transport doesn't reuse a connection in the case
  2286  // where the server replies before the request has been fully
  2287  // written. We still honor that reply (see TestIssue3595), but don't
  2288  // send future requests on the connection because it's then in a
  2289  // questionable state.
  2290  // golang.org/issue/7569
  2291  func TestTransportNoReuseAfterEarlyResponse(t *testing.T) {
  2292  	defer afterTest(t)
  2293  	var sconn struct {
  2294  		sync.Mutex
  2295  		c net.Conn
  2296  	}
  2297  	var getOkay bool
  2298  	closeConn := func() {
  2299  		sconn.Lock()
  2300  		defer sconn.Unlock()
  2301  		if sconn.c != nil {
  2302  			sconn.c.Close()
  2303  			sconn.c = nil
  2304  			if !getOkay {
  2305  				t.Logf("Closed server connection")
  2306  			}
  2307  		}
  2308  	}
  2309  	defer closeConn()
  2310  
  2311  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2312  		if r.Method == "GET" {
  2313  			io.WriteString(w, "bar")
  2314  			return
  2315  		}
  2316  		conn, _, _ := w.(Hijacker).Hijack()
  2317  		sconn.Lock()
  2318  		sconn.c = conn
  2319  		sconn.Unlock()
  2320  		conn.Write([]byte("HTTP/1.1 200 OK\r\nContent-Length: 3\r\n\r\nfoo")) // keep-alive
  2321  		go io.Copy(ioutil.Discard, conn)
  2322  	}))
  2323  	defer ts.Close()
  2324  	tr := &Transport{}
  2325  	defer tr.CloseIdleConnections()
  2326  	client := &Client{Transport: tr}
  2327  
  2328  	const bodySize = 256 << 10
  2329  	finalBit := make(byteFromChanReader, 1)
  2330  	req, _ := NewRequest("POST", ts.URL, io.MultiReader(io.LimitReader(neverEnding('x'), bodySize-1), finalBit))
  2331  	req.ContentLength = bodySize
  2332  	res, err := client.Do(req)
  2333  	if err := wantBody(res, err, "foo"); err != nil {
  2334  		t.Errorf("POST response: %v", err)
  2335  	}
  2336  	donec := make(chan bool)
  2337  	go func() {
  2338  		defer close(donec)
  2339  		res, err = client.Get(ts.URL)
  2340  		if err := wantBody(res, err, "bar"); err != nil {
  2341  			t.Errorf("GET response: %v", err)
  2342  			return
  2343  		}
  2344  		getOkay = true // suppress test noise
  2345  	}()
  2346  	time.AfterFunc(5*time.Second, closeConn)
  2347  	select {
  2348  	case <-donec:
  2349  		finalBit <- 'x' // unblock the writeloop of the first Post
  2350  		close(finalBit)
  2351  	case <-time.After(7 * time.Second):
  2352  		t.Fatal("timeout waiting for GET request to finish")
  2353  	}
  2354  }
  2355  
  2356  // Tests that we don't leak Transport persistConn.readLoop goroutines
  2357  // when a server hangs up immediately after saying it would keep-alive.
  2358  func TestTransportIssue10457(t *testing.T) {
  2359  	defer afterTest(t) // used to fail in goroutine leak check
  2360  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2361  		// Send a response with no body, keep-alive
  2362  		// (implicit), and then lie and immediately close the
  2363  		// connection. This forces the Transport's readLoop to
  2364  		// immediately Peek an io.EOF and get to the point
  2365  		// that used to hang.
  2366  		conn, _, _ := w.(Hijacker).Hijack()
  2367  		conn.Write([]byte("HTTP/1.1 200 OK\r\nFoo: Bar\r\nContent-Length: 0\r\n\r\n")) // keep-alive
  2368  		conn.Close()
  2369  	}))
  2370  	defer ts.Close()
  2371  	tr := &Transport{}
  2372  	defer tr.CloseIdleConnections()
  2373  	cl := &Client{Transport: tr}
  2374  	res, err := cl.Get(ts.URL)
  2375  	if err != nil {
  2376  		t.Fatalf("Get: %v", err)
  2377  	}
  2378  	defer res.Body.Close()
  2379  
  2380  	// Just a sanity check that we at least get the response. The real
  2381  	// test here is that the "defer afterTest" above doesn't find any
  2382  	// leaked goroutines.
  2383  	if got, want := res.Header.Get("Foo"), "Bar"; got != want {
  2384  		t.Errorf("Foo header = %q; want %q", got, want)
  2385  	}
  2386  }
  2387  
  2388  type errorReader struct {
  2389  	err error
  2390  }
  2391  
  2392  func (e errorReader) Read(p []byte) (int, error) { return 0, e.err }
  2393  
  2394  type plan9SleepReader struct{}
  2395  
  2396  func (plan9SleepReader) Read(p []byte) (int, error) {
  2397  	if runtime.GOOS == "plan9" {
  2398  		// After the fix to unblock TCP Reads in
  2399  		// https://golang.org/cl/15941, this sleep is required
  2400  		// on plan9 to make sure TCP Writes before an
  2401  		// immediate TCP close go out on the wire.  On Plan 9,
  2402  		// it seems that a hangup of a TCP connection with
  2403  		// queued data doesn't send the queued data first.
  2404  		// https://golang.org/issue/9554
  2405  		time.Sleep(50 * time.Millisecond)
  2406  	}
  2407  	return 0, io.EOF
  2408  }
  2409  
  2410  type closerFunc func() error
  2411  
  2412  func (f closerFunc) Close() error { return f() }
  2413  
  2414  // Issue 4677. If we try to reuse a connection that the server is in the
  2415  // process of closing, we may end up successfully writing out our request (or a
  2416  // portion of our request) only to find a connection error when we try to read
  2417  // from (or finish writing to) the socket.
  2418  //
  2419  // NOTE: we resend a request only if the request is idempotent, we reused a
  2420  // keep-alive connection, and we haven't yet received any header data.  This
  2421  // automatically prevents an infinite resend loop because we'll run out of the
  2422  // cached keep-alive connections eventually.
  2423  func TestRetryIdempotentRequestsOnError(t *testing.T) {
  2424  	defer afterTest(t)
  2425  
  2426  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2427  	}))
  2428  	defer ts.Close()
  2429  
  2430  	tr := &Transport{}
  2431  	c := &Client{Transport: tr}
  2432  
  2433  	const N = 2
  2434  	retryc := make(chan struct{}, N)
  2435  	SetRoundTripRetried(func() {
  2436  		retryc <- struct{}{}
  2437  	})
  2438  	defer SetRoundTripRetried(nil)
  2439  
  2440  	for n := 0; n < 100; n++ {
  2441  		// open 2 conns
  2442  		errc := make(chan error, N)
  2443  		for i := 0; i < N; i++ {
  2444  			// start goroutines, send on errc
  2445  			go func() {
  2446  				res, err := c.Get(ts.URL)
  2447  				if err == nil {
  2448  					res.Body.Close()
  2449  				}
  2450  				errc <- err
  2451  			}()
  2452  		}
  2453  		for i := 0; i < N; i++ {
  2454  			if err := <-errc; err != nil {
  2455  				t.Fatal(err)
  2456  			}
  2457  		}
  2458  
  2459  		ts.CloseClientConnections()
  2460  		for i := 0; i < N; i++ {
  2461  			go func() {
  2462  				res, err := c.Get(ts.URL)
  2463  				if err == nil {
  2464  					res.Body.Close()
  2465  				}
  2466  				errc <- err
  2467  			}()
  2468  		}
  2469  
  2470  		for i := 0; i < N; i++ {
  2471  			if err := <-errc; err != nil {
  2472  				t.Fatal(err)
  2473  			}
  2474  		}
  2475  		for i := 0; i < N; i++ {
  2476  			select {
  2477  			case <-retryc:
  2478  				// we triggered a retry, test was successful
  2479  				t.Logf("finished after %d runs\n", n)
  2480  				return
  2481  			default:
  2482  			}
  2483  		}
  2484  	}
  2485  	t.Fatal("did not trigger any retries")
  2486  }
  2487  
  2488  // Issue 6981
  2489  func TestTransportClosesBodyOnError(t *testing.T) {
  2490  	defer afterTest(t)
  2491  	readBody := make(chan error, 1)
  2492  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2493  		_, err := ioutil.ReadAll(r.Body)
  2494  		readBody <- err
  2495  	}))
  2496  	defer ts.Close()
  2497  	fakeErr := errors.New("fake error")
  2498  	didClose := make(chan bool, 1)
  2499  	req, _ := NewRequest("POST", ts.URL, struct {
  2500  		io.Reader
  2501  		io.Closer
  2502  	}{
  2503  		io.MultiReader(io.LimitReader(neverEnding('x'), 1<<20), plan9SleepReader{}, errorReader{fakeErr}),
  2504  		closerFunc(func() error {
  2505  			select {
  2506  			case didClose <- true:
  2507  			default:
  2508  			}
  2509  			return nil
  2510  		}),
  2511  	})
  2512  	res, err := DefaultClient.Do(req)
  2513  	if res != nil {
  2514  		defer res.Body.Close()
  2515  	}
  2516  	if err == nil || !strings.Contains(err.Error(), fakeErr.Error()) {
  2517  		t.Fatalf("Do error = %v; want something containing %q", err, fakeErr.Error())
  2518  	}
  2519  	select {
  2520  	case err := <-readBody:
  2521  		if err == nil {
  2522  			t.Errorf("Unexpected success reading request body from handler; want 'unexpected EOF reading trailer'")
  2523  		}
  2524  	case <-time.After(5 * time.Second):
  2525  		t.Error("timeout waiting for server handler to complete")
  2526  	}
  2527  	select {
  2528  	case <-didClose:
  2529  	default:
  2530  		t.Errorf("didn't see Body.Close")
  2531  	}
  2532  }
  2533  
  2534  func TestTransportDialTLS(t *testing.T) {
  2535  	var mu sync.Mutex // guards following
  2536  	var gotReq, didDial bool
  2537  
  2538  	ts := httptest.NewTLSServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2539  		mu.Lock()
  2540  		gotReq = true
  2541  		mu.Unlock()
  2542  	}))
  2543  	defer ts.Close()
  2544  	tr := &Transport{
  2545  		DialTLS: func(netw, addr string) (net.Conn, error) {
  2546  			mu.Lock()
  2547  			didDial = true
  2548  			mu.Unlock()
  2549  			c, err := tls.Dial(netw, addr, &tls.Config{
  2550  				InsecureSkipVerify: true,
  2551  			})
  2552  			if err != nil {
  2553  				return nil, err
  2554  			}
  2555  			return c, c.Handshake()
  2556  		},
  2557  	}
  2558  	defer tr.CloseIdleConnections()
  2559  	client := &Client{Transport: tr}
  2560  	res, err := client.Get(ts.URL)
  2561  	if err != nil {
  2562  		t.Fatal(err)
  2563  	}
  2564  	res.Body.Close()
  2565  	mu.Lock()
  2566  	if !gotReq {
  2567  		t.Error("didn't get request")
  2568  	}
  2569  	if !didDial {
  2570  		t.Error("didn't use dial hook")
  2571  	}
  2572  }
  2573  
  2574  // Test for issue 8755
  2575  // Ensure that if a proxy returns an error, it is exposed by RoundTrip
  2576  func TestRoundTripReturnsProxyError(t *testing.T) {
  2577  	badProxy := func(*Request) (*url.URL, error) {
  2578  		return nil, errors.New("errorMessage")
  2579  	}
  2580  
  2581  	tr := &Transport{Proxy: badProxy}
  2582  
  2583  	req, _ := NewRequest("GET", "http://example.com", nil)
  2584  
  2585  	_, err := tr.RoundTrip(req)
  2586  
  2587  	if err == nil {
  2588  		t.Error("Expected proxy error to be returned by RoundTrip")
  2589  	}
  2590  }
  2591  
  2592  // tests that putting an idle conn after a call to CloseIdleConns does return it
  2593  func TestTransportCloseIdleConnsThenReturn(t *testing.T) {
  2594  	tr := &Transport{}
  2595  	wantIdle := func(when string, n int) bool {
  2596  		got := tr.IdleConnCountForTesting("|http|example.com") // key used by PutIdleTestConn
  2597  		if got == n {
  2598  			return true
  2599  		}
  2600  		t.Errorf("%s: idle conns = %d; want %d", when, got, n)
  2601  		return false
  2602  	}
  2603  	wantIdle("start", 0)
  2604  	if !tr.PutIdleTestConn() {
  2605  		t.Fatal("put failed")
  2606  	}
  2607  	if !tr.PutIdleTestConn() {
  2608  		t.Fatal("second put failed")
  2609  	}
  2610  	wantIdle("after put", 2)
  2611  	tr.CloseIdleConnections()
  2612  	if !tr.IsIdleForTesting() {
  2613  		t.Error("should be idle after CloseIdleConnections")
  2614  	}
  2615  	wantIdle("after close idle", 0)
  2616  	if tr.PutIdleTestConn() {
  2617  		t.Fatal("put didn't fail")
  2618  	}
  2619  	wantIdle("after second put", 0)
  2620  
  2621  	tr.RequestIdleConnChForTesting() // should toggle the transport out of idle mode
  2622  	if tr.IsIdleForTesting() {
  2623  		t.Error("shouldn't be idle after RequestIdleConnChForTesting")
  2624  	}
  2625  	if !tr.PutIdleTestConn() {
  2626  		t.Fatal("after re-activation")
  2627  	}
  2628  	wantIdle("after final put", 1)
  2629  }
  2630  
  2631  // This tests that an client requesting a content range won't also
  2632  // implicitly ask for gzip support. If they want that, they need to do it
  2633  // on their own.
  2634  // golang.org/issue/8923
  2635  func TestTransportRangeAndGzip(t *testing.T) {
  2636  	defer afterTest(t)
  2637  	reqc := make(chan *Request, 1)
  2638  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2639  		reqc <- r
  2640  	}))
  2641  	defer ts.Close()
  2642  
  2643  	req, _ := NewRequest("GET", ts.URL, nil)
  2644  	req.Header.Set("Range", "bytes=7-11")
  2645  	res, err := DefaultClient.Do(req)
  2646  	if err != nil {
  2647  		t.Fatal(err)
  2648  	}
  2649  
  2650  	select {
  2651  	case r := <-reqc:
  2652  		if strings.Contains(r.Header.Get("Accept-Encoding"), "gzip") {
  2653  			t.Error("Transport advertised gzip support in the Accept header")
  2654  		}
  2655  		if r.Header.Get("Range") == "" {
  2656  			t.Error("no Range in request")
  2657  		}
  2658  	case <-time.After(10 * time.Second):
  2659  		t.Fatal("timeout")
  2660  	}
  2661  	res.Body.Close()
  2662  }
  2663  
  2664  // Previously, we used to handle a logical race within RoundTrip by waiting for 100ms
  2665  // in the case of an error. Changing the order of the channel operations got rid of this
  2666  // race.
  2667  //
  2668  // In order to test that the channel op reordering works, we install a hook into the
  2669  // roundTrip function which gets called if we saw the connection go away and
  2670  // we subsequently received a response.
  2671  func TestTransportResponseCloseRace(t *testing.T) {
  2672  	if testing.Short() {
  2673  		t.Skip("skipping in short mode")
  2674  	}
  2675  	defer afterTest(t)
  2676  
  2677  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2678  	}))
  2679  	defer ts.Close()
  2680  	sawRace := false
  2681  	SetInstallConnClosedHook(func() {
  2682  		sawRace = true
  2683  	})
  2684  	defer SetInstallConnClosedHook(nil)
  2685  
  2686  	SetTestHookWaitResLoop(func() {
  2687  		// Make the select race much more likely by blocking before
  2688  		// the select, so both will be ready by the time the
  2689  		// select runs.
  2690  		time.Sleep(50 * time.Millisecond)
  2691  	})
  2692  	defer SetTestHookWaitResLoop(nil)
  2693  
  2694  	tr := &Transport{
  2695  		DisableKeepAlives: true,
  2696  	}
  2697  	req, err := NewRequest("GET", ts.URL, nil)
  2698  	if err != nil {
  2699  		t.Fatal(err)
  2700  	}
  2701  	// selects are not deterministic, so do this a bunch
  2702  	// and see if we handle the logical race at least once.
  2703  	for i := 0; i < 10000; i++ {
  2704  		resp, err := tr.RoundTrip(req)
  2705  		if err != nil {
  2706  			t.Fatalf("unexpected error: %s", err)
  2707  			continue
  2708  		}
  2709  		resp.Body.Close()
  2710  		if sawRace {
  2711  			t.Logf("saw race after %d iterations", i+1)
  2712  			break
  2713  		}
  2714  	}
  2715  	if !sawRace {
  2716  		t.Errorf("didn't see response/connection going away race")
  2717  	}
  2718  }
  2719  
  2720  // Test for issue 10474
  2721  func TestTransportResponseCancelRace(t *testing.T) {
  2722  	defer afterTest(t)
  2723  
  2724  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2725  		// important that this response has a body.
  2726  		var b [1024]byte
  2727  		w.Write(b[:])
  2728  	}))
  2729  	defer ts.Close()
  2730  
  2731  	tr := &Transport{}
  2732  	defer tr.CloseIdleConnections()
  2733  
  2734  	req, err := NewRequest("GET", ts.URL, nil)
  2735  	if err != nil {
  2736  		t.Fatal(err)
  2737  	}
  2738  	res, err := tr.RoundTrip(req)
  2739  	if err != nil {
  2740  		t.Fatal(err)
  2741  	}
  2742  	// If we do an early close, Transport just throws the connection away and
  2743  	// doesn't reuse it. In order to trigger the bug, it has to reuse the connection
  2744  	// so read the body
  2745  	if _, err := io.Copy(ioutil.Discard, res.Body); err != nil {
  2746  		t.Fatal(err)
  2747  	}
  2748  
  2749  	req2, err := NewRequest("GET", ts.URL, nil)
  2750  	if err != nil {
  2751  		t.Fatal(err)
  2752  	}
  2753  	tr.CancelRequest(req)
  2754  	res, err = tr.RoundTrip(req2)
  2755  	if err != nil {
  2756  		t.Fatal(err)
  2757  	}
  2758  	res.Body.Close()
  2759  }
  2760  
  2761  func TestTransportDialCancelRace(t *testing.T) {
  2762  	defer afterTest(t)
  2763  
  2764  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {}))
  2765  	defer ts.Close()
  2766  
  2767  	tr := &Transport{}
  2768  	defer tr.CloseIdleConnections()
  2769  
  2770  	req, err := NewRequest("GET", ts.URL, nil)
  2771  	if err != nil {
  2772  		t.Fatal(err)
  2773  	}
  2774  	SetEnterRoundTripHook(func() {
  2775  		tr.CancelRequest(req)
  2776  	})
  2777  	defer SetEnterRoundTripHook(nil)
  2778  	res, err := tr.RoundTrip(req)
  2779  	if err != ExportErrRequestCanceled {
  2780  		t.Errorf("expected canceled request error; got %v", err)
  2781  		if err == nil {
  2782  			res.Body.Close()
  2783  		}
  2784  	}
  2785  }
  2786  
  2787  // logWritesConn is a net.Conn that logs each Write call to writes
  2788  // and then proxies to w.
  2789  // It proxies Read calls to a reader it receives from rch.
  2790  type logWritesConn struct {
  2791  	net.Conn // nil. crash on use.
  2792  
  2793  	w io.Writer
  2794  
  2795  	rch <-chan io.Reader
  2796  	r   io.Reader // nil until received by rch
  2797  
  2798  	mu     sync.Mutex
  2799  	writes []string
  2800  }
  2801  
  2802  func (c *logWritesConn) Write(p []byte) (n int, err error) {
  2803  	c.mu.Lock()
  2804  	defer c.mu.Unlock()
  2805  	c.writes = append(c.writes, string(p))
  2806  	return c.w.Write(p)
  2807  }
  2808  
  2809  func (c *logWritesConn) Read(p []byte) (n int, err error) {
  2810  	if c.r == nil {
  2811  		c.r = <-c.rch
  2812  	}
  2813  	return c.r.Read(p)
  2814  }
  2815  
  2816  func (c *logWritesConn) Close() error { return nil }
  2817  
  2818  // Issue 6574
  2819  func TestTransportFlushesBodyChunks(t *testing.T) {
  2820  	defer afterTest(t)
  2821  	resBody := make(chan io.Reader, 1)
  2822  	connr, connw := io.Pipe() // connection pipe pair
  2823  	lw := &logWritesConn{
  2824  		rch: resBody,
  2825  		w:   connw,
  2826  	}
  2827  	tr := &Transport{
  2828  		Dial: func(network, addr string) (net.Conn, error) {
  2829  			return lw, nil
  2830  		},
  2831  	}
  2832  	bodyr, bodyw := io.Pipe() // body pipe pair
  2833  	go func() {
  2834  		defer bodyw.Close()
  2835  		for i := 0; i < 3; i++ {
  2836  			fmt.Fprintf(bodyw, "num%d\n", i)
  2837  		}
  2838  	}()
  2839  	resc := make(chan *Response)
  2840  	go func() {
  2841  		req, _ := NewRequest("POST", "http://localhost:8080", bodyr)
  2842  		req.Header.Set("User-Agent", "x") // known value for test
  2843  		res, err := tr.RoundTrip(req)
  2844  		if err != nil {
  2845  			t.Errorf("RoundTrip: %v", err)
  2846  			close(resc)
  2847  			return
  2848  		}
  2849  		resc <- res
  2850  
  2851  	}()
  2852  	// Fully consume the request before checking the Write log vs. want.
  2853  	req, err := ReadRequest(bufio.NewReader(connr))
  2854  	if err != nil {
  2855  		t.Fatal(err)
  2856  	}
  2857  	io.Copy(ioutil.Discard, req.Body)
  2858  
  2859  	// Unblock the transport's roundTrip goroutine.
  2860  	resBody <- strings.NewReader("HTTP/1.1 204 No Content\r\nConnection: close\r\n\r\n")
  2861  	res, ok := <-resc
  2862  	if !ok {
  2863  		return
  2864  	}
  2865  	defer res.Body.Close()
  2866  
  2867  	want := []string{
  2868  		// Because Request.ContentLength = 0, the body is sniffed for 1 byte to determine whether there's content.
  2869  		// That explains the initial "num0" being split into "n" and "um0".
  2870  		// The first byte is included with the request headers Write. Perhaps in the future
  2871  		// we will want to flush the headers out early if the first byte of the request body is
  2872  		// taking a long time to arrive. But not yet.
  2873  		"POST / HTTP/1.1\r\nHost: localhost:8080\r\nUser-Agent: x\r\nTransfer-Encoding: chunked\r\nAccept-Encoding: gzip\r\n\r\n" +
  2874  			"1\r\nn\r\n",
  2875  		"4\r\num0\n\r\n",
  2876  		"5\r\nnum1\n\r\n",
  2877  		"5\r\nnum2\n\r\n",
  2878  		"0\r\n\r\n",
  2879  	}
  2880  	if !reflect.DeepEqual(lw.writes, want) {
  2881  		t.Errorf("Writes differed.\n Got: %q\nWant: %q\n", lw.writes, want)
  2882  	}
  2883  }
  2884  
  2885  // Issue 11745.
  2886  func TestTransportPrefersResponseOverWriteError(t *testing.T) {
  2887  	if testing.Short() {
  2888  		t.Skip("skipping in short mode")
  2889  	}
  2890  	defer afterTest(t)
  2891  	const contentLengthLimit = 1024 * 1024 // 1MB
  2892  	ts := httptest.NewServer(HandlerFunc(func(w ResponseWriter, r *Request) {
  2893  		if r.ContentLength >= contentLengthLimit {
  2894  			w.WriteHeader(StatusBadRequest)
  2895  			r.Body.Close()
  2896  			return
  2897  		}
  2898  		w.WriteHeader(StatusOK)
  2899  	}))
  2900  	defer ts.Close()
  2901  
  2902  	fail := 0
  2903  	count := 100
  2904  	bigBody := strings.Repeat("a", contentLengthLimit*2)
  2905  	for i := 0; i < count; i++ {
  2906  		req, err := NewRequest("PUT", ts.URL, strings.NewReader(bigBody))
  2907  		if err != nil {
  2908  			t.Fatal(err)
  2909  		}
  2910  		tr := new(Transport)
  2911  		defer tr.CloseIdleConnections()
  2912  		client := &Client{Transport: tr}
  2913  		resp, err := client.Do(req)
  2914  		if err != nil {
  2915  			fail++
  2916  			t.Logf("%d = %#v", i, err)
  2917  			if ue, ok := err.(*url.Error); ok {
  2918  				t.Logf("urlErr = %#v", ue.Err)
  2919  				if ne, ok := ue.Err.(*net.OpError); ok {
  2920  					t.Logf("netOpError = %#v", ne.Err)
  2921  				}
  2922  			}
  2923  		} else {
  2924  			resp.Body.Close()
  2925  			if resp.StatusCode != 400 {
  2926  				t.Errorf("Expected status code 400, got %v", resp.Status)
  2927  			}
  2928  		}
  2929  	}
  2930  	if fail > 0 {
  2931  		t.Errorf("Failed %v out of %v\n", fail, count)
  2932  	}
  2933  }
  2934  
  2935  func TestTransportAutomaticHTTP2(t *testing.T) {
  2936  	tr := &Transport{}
  2937  	_, err := tr.RoundTrip(new(Request))
  2938  	if err == nil {
  2939  		t.Error("expected error from RoundTrip")
  2940  	}
  2941  	if tr.TLSNextProto["h2"] == nil {
  2942  		t.Errorf("HTTP/2 not registered.")
  2943  	}
  2944  
  2945  	// Now with TLSNextProto set:
  2946  	tr = &Transport{TLSNextProto: make(map[string]func(string, *tls.Conn) RoundTripper)}
  2947  	_, err = tr.RoundTrip(new(Request))
  2948  	if err == nil {
  2949  		t.Error("expected error from RoundTrip")
  2950  	}
  2951  	if tr.TLSNextProto["h2"] != nil {
  2952  		t.Errorf("HTTP/2 registered, despite non-nil TLSNextProto field")
  2953  	}
  2954  }
  2955  
  2956  func wantBody(res *Response, err error, want string) error {
  2957  	if err != nil {
  2958  		return err
  2959  	}
  2960  	slurp, err := ioutil.ReadAll(res.Body)
  2961  	if err != nil {
  2962  		return fmt.Errorf("error reading body: %v", err)
  2963  	}
  2964  	if string(slurp) != want {
  2965  		return fmt.Errorf("body = %q; want %q", slurp, want)
  2966  	}
  2967  	if err := res.Body.Close(); err != nil {
  2968  		return fmt.Errorf("body Close = %v", err)
  2969  	}
  2970  	return nil
  2971  }
  2972  
  2973  func newLocalListener(t *testing.T) net.Listener {
  2974  	ln, err := net.Listen("tcp", "127.0.0.1:0")
  2975  	if err != nil {
  2976  		ln, err = net.Listen("tcp6", "[::1]:0")
  2977  	}
  2978  	if err != nil {
  2979  		t.Fatal(err)
  2980  	}
  2981  	return ln
  2982  }
  2983  
  2984  type countCloseReader struct {
  2985  	n *int
  2986  	io.Reader
  2987  }
  2988  
  2989  func (cr countCloseReader) Close() error {
  2990  	(*cr.n)++
  2991  	return nil
  2992  }
  2993  
  2994  // rgz is a gzip quine that uncompresses to itself.
  2995  var rgz = []byte{
  2996  	0x1f, 0x8b, 0x08, 0x08, 0x00, 0x00, 0x00, 0x00,
  2997  	0x00, 0x00, 0x72, 0x65, 0x63, 0x75, 0x72, 0x73,
  2998  	0x69, 0x76, 0x65, 0x00, 0x92, 0xef, 0xe6, 0xe0,
  2999  	0x60, 0x00, 0x83, 0xa2, 0xd4, 0xe4, 0xd2, 0xa2,
  3000  	0xe2, 0xcc, 0xb2, 0x54, 0x06, 0x00, 0x00, 0x17,
  3001  	0x00, 0xe8, 0xff, 0x92, 0xef, 0xe6, 0xe0, 0x60,
  3002  	0x00, 0x83, 0xa2, 0xd4, 0xe4, 0xd2, 0xa2, 0xe2,
  3003  	0xcc, 0xb2, 0x54, 0x06, 0x00, 0x00, 0x17, 0x00,
  3004  	0xe8, 0xff, 0x42, 0x12, 0x46, 0x16, 0x06, 0x00,
  3005  	0x05, 0x00, 0xfa, 0xff, 0x42, 0x12, 0x46, 0x16,
  3006  	0x06, 0x00, 0x05, 0x00, 0xfa, 0xff, 0x00, 0x05,
  3007  	0x00, 0xfa, 0xff, 0x00, 0x14, 0x00, 0xeb, 0xff,
  3008  	0x42, 0x12, 0x46, 0x16, 0x06, 0x00, 0x05, 0x00,
  3009  	0xfa, 0xff, 0x00, 0x05, 0x00, 0xfa, 0xff, 0x00,
  3010  	0x14, 0x00, 0xeb, 0xff, 0x42, 0x88, 0x21, 0xc4,
  3011  	0x00, 0x00, 0x14, 0x00, 0xeb, 0xff, 0x42, 0x88,
  3012  	0x21, 0xc4, 0x00, 0x00, 0x14, 0x00, 0xeb, 0xff,
  3013  	0x42, 0x88, 0x21, 0xc4, 0x00, 0x00, 0x14, 0x00,
  3014  	0xeb, 0xff, 0x42, 0x88, 0x21, 0xc4, 0x00, 0x00,
  3015  	0x14, 0x00, 0xeb, 0xff, 0x42, 0x88, 0x21, 0xc4,
  3016  	0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0x00, 0x00,
  3017  	0x00, 0xff, 0xff, 0x00, 0x17, 0x00, 0xe8, 0xff,
  3018  	0x42, 0x88, 0x21, 0xc4, 0x00, 0x00, 0x00, 0x00,
  3019  	0xff, 0xff, 0x00, 0x00, 0x00, 0xff, 0xff, 0x00,
  3020  	0x17, 0x00, 0xe8, 0xff, 0x42, 0x12, 0x46, 0x16,
  3021  	0x06, 0x00, 0x00, 0x00, 0xff, 0xff, 0x01, 0x08,
  3022  	0x00, 0xf7, 0xff, 0x3d, 0xb1, 0x20, 0x85, 0xfa,
  3023  	0x00, 0x00, 0x00, 0x42, 0x12, 0x46, 0x16, 0x06,
  3024  	0x00, 0x00, 0x00, 0xff, 0xff, 0x01, 0x08, 0x00,
  3025  	0xf7, 0xff, 0x3d, 0xb1, 0x20, 0x85, 0xfa, 0x00,
  3026  	0x00, 0x00, 0x3d, 0xb1, 0x20, 0x85, 0xfa, 0x00,
  3027  	0x00, 0x00,
  3028  }