@@ -474,6 +474,56 @@ func testTransportReadToEndReusesConn(t *testing.T, mode testMode) {
474474	}
475475}
476476
477+ // Tests that the HTTP transport re-uses connections when a client 
478+ // early closes a response Body but the content is fully read into the underlying 
479+ // buffer. So we can discard the body buffer and reuse the connection. 
480+ func  TestTransportReusesEarlyCloseButAllReceivedConn (t  * testing.T ) {
481+ 	run (t , testTransportReusesEarlyCloseButAllReceivedConn )
482+ }
483+ func  testTransportReusesEarlyCloseButAllReceivedConn (t  * testing.T , mode  testMode ) {
484+ 	const  msg  =  "foobar" 
485+ 
486+ 	var  addrSeen  map [string ]int 
487+ 	ts  :=  newClientServerTest (t , mode , HandlerFunc (func (w  ResponseWriter , r  * Request ) {
488+ 		addrSeen [r .RemoteAddr ]++ 
489+ 		w .Header ().Set ("Content-Length" , strconv .Itoa (len (msg )))
490+ 		w .WriteHeader (200 )
491+ 		w .Write ([]byte (msg ))
492+ 	})).ts 
493+ 
494+ 	wantLen  :=  len (msg )
495+ 	addrSeen  =  make (map [string ]int )
496+ 	total  :=  5 
497+ 	for  i  :=  0 ; i  <  total ; i ++  {
498+ 		res , err  :=  ts .Client ().Get (ts .URL )
499+ 		if  err  !=  nil  {
500+ 			t .Errorf ("Get /: %v" , err )
501+ 			continue 
502+ 		}
503+ 
504+ 		if  res .ContentLength  !=  int64 (wantLen ) {
505+ 			t .Errorf ("res.ContentLength = %d; want %d" , res .ContentLength , wantLen )
506+ 		}
507+ 
508+ 		if  i + 1  <  total  {
509+ 			// Close body directly. The body is small enough, so probably the underlying bufio.Reader 
510+ 			// has read entire body into buffer. Thus even if the body is not read, the buffer is discarded 
511+ 			// then connection is reused. 
512+ 			res .Body .Close ()
513+ 		} else  {
514+ 			// when reading body, everything should be same. 
515+ 			got , err  :=  io .ReadAll (res .Body )
516+ 			if  string (got ) !=  msg  ||  err  !=  nil  {
517+ 				t .Errorf ("ReadAll(Body) = %q, %v; want %q, nil" , string (got ), err , msg )
518+ 			}
519+ 		}
520+ 	}
521+ 
522+ 	if  len (addrSeen ) !=  1  {
523+ 		t .Errorf ("server saw %d distinct client addresses; want 1" , len (addrSeen ))
524+ 	}
525+ }
526+ 
477527func  TestTransportMaxPerHostIdleConns (t  * testing.T ) {
478528	run (t , testTransportMaxPerHostIdleConns , []testMode {http1Mode })
479529}
0 commit comments