mirror of https://github.com/golang/go.git
all: enable disabled HTTP/2 tests
Update net/http to enable tests that pass with the latest update to the vendored x/net. Update a few tests: Windows apparently doesn't guarantee that time.Since(time.Now()) is >=0, so to set a definitely-expired write deadline, use a time firmly in the past rather than now. Put a backoff loop on TestServerReadTimeout to avoid failures when the timeout expires mid-TLS-handshake. (The TLS handshake timeout is set to min(ReadTimeout, WriteTimeout, ReadHeaderTimeout); there's no way to set a long TLS handshake timeout and a short read timeout.) Don't close the http.Server in TestServerWriteTimeout while the handler may still be executing, since this can result in us getting the wrong error. Change the GOOS=js fake net implementation to properly return ErrDeadlineExceeded when a read/write deadline is exceeded, rather than EAGAIN. For #49837 For #54136 Change-Id: Id8a4ff6ac58336ff212dda3c8799b320cd6b9c19 Reviewed-on: https://go-review.googlesource.com/c/go/+/449935 Reviewed-by: Bryan Mills <bcmills@google.com> Run-TryBot: Damien Neil <dneil@google.com> TryBot-Result: Gopher Robot <gobot@golang.org>
This commit is contained in:
parent
69ca0a859c
commit
21015cf6ba
|
|
@ -13,9 +13,6 @@ import (
|
||||||
|
|
||||||
func TestResponseControllerFlush(t *testing.T) { run(t, testResponseControllerFlush) }
|
func TestResponseControllerFlush(t *testing.T) { run(t, testResponseControllerFlush) }
|
||||||
func testResponseControllerFlush(t *testing.T, mode testMode) {
|
func testResponseControllerFlush(t *testing.T, mode testMode) {
|
||||||
if mode == http2Mode {
|
|
||||||
t.Skip("skip until h2_bundle.go is updated")
|
|
||||||
}
|
|
||||||
continuec := make(chan struct{})
|
continuec := make(chan struct{})
|
||||||
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
||||||
ctl := NewResponseController(w)
|
ctl := NewResponseController(w)
|
||||||
|
|
@ -49,9 +46,6 @@ func testResponseControllerFlush(t *testing.T, mode testMode) {
|
||||||
|
|
||||||
func TestResponseControllerHijack(t *testing.T) { run(t, testResponseControllerHijack) }
|
func TestResponseControllerHijack(t *testing.T) { run(t, testResponseControllerHijack) }
|
||||||
func testResponseControllerHijack(t *testing.T, mode testMode) {
|
func testResponseControllerHijack(t *testing.T, mode testMode) {
|
||||||
if mode == http2Mode {
|
|
||||||
t.Skip("skip until h2_bundle.go is updated")
|
|
||||||
}
|
|
||||||
const header = "X-Header"
|
const header = "X-Header"
|
||||||
const value = "set"
|
const value = "set"
|
||||||
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
||||||
|
|
@ -83,16 +77,13 @@ func TestResponseControllerSetPastWriteDeadline(t *testing.T) {
|
||||||
run(t, testResponseControllerSetPastWriteDeadline)
|
run(t, testResponseControllerSetPastWriteDeadline)
|
||||||
}
|
}
|
||||||
func testResponseControllerSetPastWriteDeadline(t *testing.T, mode testMode) {
|
func testResponseControllerSetPastWriteDeadline(t *testing.T, mode testMode) {
|
||||||
if mode == http2Mode {
|
|
||||||
t.Skip("skip until h2_bundle.go is updated")
|
|
||||||
}
|
|
||||||
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
||||||
ctl := NewResponseController(w)
|
ctl := NewResponseController(w)
|
||||||
w.Write([]byte("one"))
|
w.Write([]byte("one"))
|
||||||
if err := ctl.Flush(); err != nil {
|
if err := ctl.Flush(); err != nil {
|
||||||
t.Errorf("before setting deadline: ctl.Flush() = %v, want nil", err)
|
t.Errorf("before setting deadline: ctl.Flush() = %v, want nil", err)
|
||||||
}
|
}
|
||||||
if err := ctl.SetWriteDeadline(time.Now()); err != nil {
|
if err := ctl.SetWriteDeadline(time.Now().Add(-10 * time.Second)); err != nil {
|
||||||
t.Errorf("ctl.SetWriteDeadline() = %v, want nil", err)
|
t.Errorf("ctl.SetWriteDeadline() = %v, want nil", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -128,9 +119,6 @@ func TestResponseControllerSetFutureWriteDeadline(t *testing.T) {
|
||||||
run(t, testResponseControllerSetFutureWriteDeadline)
|
run(t, testResponseControllerSetFutureWriteDeadline)
|
||||||
}
|
}
|
||||||
func testResponseControllerSetFutureWriteDeadline(t *testing.T, mode testMode) {
|
func testResponseControllerSetFutureWriteDeadline(t *testing.T, mode testMode) {
|
||||||
if mode == http2Mode {
|
|
||||||
t.Skip("skip until h2_bundle.go is updated")
|
|
||||||
}
|
|
||||||
errc := make(chan error, 1)
|
errc := make(chan error, 1)
|
||||||
startwritec := make(chan struct{})
|
startwritec := make(chan struct{})
|
||||||
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
||||||
|
|
@ -167,9 +155,6 @@ func TestResponseControllerSetPastReadDeadline(t *testing.T) {
|
||||||
run(t, testResponseControllerSetPastReadDeadline)
|
run(t, testResponseControllerSetPastReadDeadline)
|
||||||
}
|
}
|
||||||
func testResponseControllerSetPastReadDeadline(t *testing.T, mode testMode) {
|
func testResponseControllerSetPastReadDeadline(t *testing.T, mode testMode) {
|
||||||
if mode == http2Mode {
|
|
||||||
t.Skip("skip until h2_bundle.go is updated")
|
|
||||||
}
|
|
||||||
readc := make(chan struct{})
|
readc := make(chan struct{})
|
||||||
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
||||||
ctl := NewResponseController(w)
|
ctl := NewResponseController(w)
|
||||||
|
|
@ -223,9 +208,6 @@ func TestResponseControllerSetFutureReadDeadline(t *testing.T) {
|
||||||
run(t, testResponseControllerSetFutureReadDeadline)
|
run(t, testResponseControllerSetFutureReadDeadline)
|
||||||
}
|
}
|
||||||
func testResponseControllerSetFutureReadDeadline(t *testing.T, mode testMode) {
|
func testResponseControllerSetFutureReadDeadline(t *testing.T, mode testMode) {
|
||||||
if mode == http2Mode {
|
|
||||||
t.Skip("skip until h2_bundle.go is updated")
|
|
||||||
}
|
|
||||||
respBody := "response body"
|
respBody := "response body"
|
||||||
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, req *Request) {
|
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, req *Request) {
|
||||||
ctl := NewResponseController(w)
|
ctl := NewResponseController(w)
|
||||||
|
|
@ -261,9 +243,6 @@ func (w wrapWriter) Unwrap() ResponseWriter {
|
||||||
|
|
||||||
func TestWrappedResponseController(t *testing.T) { run(t, testWrappedResponseController) }
|
func TestWrappedResponseController(t *testing.T) { run(t, testWrappedResponseController) }
|
||||||
func testWrappedResponseController(t *testing.T, mode testMode) {
|
func testWrappedResponseController(t *testing.T, mode testMode) {
|
||||||
if mode == http2Mode {
|
|
||||||
t.Skip("skip until h2_bundle.go is updated")
|
|
||||||
}
|
|
||||||
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
cst := newClientServerTest(t, mode, HandlerFunc(func(w ResponseWriter, r *Request) {
|
||||||
ctl := NewResponseController(w)
|
ctl := NewResponseController(w)
|
||||||
if err := ctl.Flush(); err != nil {
|
if err := ctl.Flush(); err != nil {
|
||||||
|
|
|
||||||
|
|
@ -738,37 +738,37 @@ func testServerTimeoutsWithTimeout(t *testing.T, timeout time.Duration, mode tes
|
||||||
|
|
||||||
func TestServerReadTimeout(t *testing.T) { run(t, testServerReadTimeout) }
|
func TestServerReadTimeout(t *testing.T) { run(t, testServerReadTimeout) }
|
||||||
func testServerReadTimeout(t *testing.T, mode testMode) {
|
func testServerReadTimeout(t *testing.T, mode testMode) {
|
||||||
if mode == http2Mode {
|
|
||||||
t.Skip("https://go.dev/issue/49837")
|
|
||||||
}
|
|
||||||
respBody := "response body"
|
respBody := "response body"
|
||||||
cst := newClientServerTest(t, mode, HandlerFunc(func(res ResponseWriter, req *Request) {
|
for timeout := 5 * time.Millisecond; ; timeout *= 2 {
|
||||||
_, err := io.Copy(io.Discard, req.Body)
|
cst := newClientServerTest(t, mode, HandlerFunc(func(res ResponseWriter, req *Request) {
|
||||||
if !errors.Is(err, os.ErrDeadlineExceeded) {
|
_, err := io.Copy(io.Discard, req.Body)
|
||||||
t.Errorf("server timed out reading request body: got err %v; want os.ErrDeadlineExceeded", err)
|
if !errors.Is(err, os.ErrDeadlineExceeded) {
|
||||||
|
t.Errorf("server timed out reading request body: got err %v; want os.ErrDeadlineExceeded", err)
|
||||||
|
}
|
||||||
|
res.Write([]byte(respBody))
|
||||||
|
}), func(ts *httptest.Server) {
|
||||||
|
ts.Config.ReadHeaderTimeout = -1 // don't time out while reading headers
|
||||||
|
ts.Config.ReadTimeout = timeout
|
||||||
|
})
|
||||||
|
pr, pw := io.Pipe()
|
||||||
|
res, err := cst.c.Post(cst.ts.URL, "text/apocryphal", pr)
|
||||||
|
if err != nil {
|
||||||
|
t.Logf("Get error, retrying: %v", err)
|
||||||
|
cst.close()
|
||||||
|
continue
|
||||||
}
|
}
|
||||||
res.Write([]byte(respBody))
|
defer res.Body.Close()
|
||||||
}), func(ts *httptest.Server) {
|
got, err := io.ReadAll(res.Body)
|
||||||
ts.Config.ReadTimeout = 5 * time.Millisecond
|
if string(got) != respBody || err != nil {
|
||||||
})
|
t.Errorf("client read response body: %q, %v; want %q, nil", string(got), err, respBody)
|
||||||
pr, pw := io.Pipe()
|
}
|
||||||
res, err := cst.c.Post(cst.ts.URL, "text/apocryphal", pr)
|
pw.Close()
|
||||||
if err != nil {
|
break
|
||||||
t.Fatal(err)
|
|
||||||
}
|
}
|
||||||
defer res.Body.Close()
|
|
||||||
got, err := io.ReadAll(res.Body)
|
|
||||||
if string(got) != respBody || err != nil {
|
|
||||||
t.Errorf("client read response body: %q, %v; want %q, nil", string(got), err, respBody)
|
|
||||||
}
|
|
||||||
pw.Close()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestServerWriteTimeout(t *testing.T) { run(t, testServerWriteTimeout) }
|
func TestServerWriteTimeout(t *testing.T) { run(t, testServerWriteTimeout) }
|
||||||
func testServerWriteTimeout(t *testing.T, mode testMode) {
|
func testServerWriteTimeout(t *testing.T, mode testMode) {
|
||||||
if mode == http2Mode {
|
|
||||||
t.Skip("https://go.dev/issue/56478")
|
|
||||||
}
|
|
||||||
for timeout := 5 * time.Millisecond; ; timeout *= 2 {
|
for timeout := 5 * time.Millisecond; ; timeout *= 2 {
|
||||||
errc := make(chan error, 2)
|
errc := make(chan error, 2)
|
||||||
cst := newClientServerTest(t, mode, HandlerFunc(func(res ResponseWriter, req *Request) {
|
cst := newClientServerTest(t, mode, HandlerFunc(func(res ResponseWriter, req *Request) {
|
||||||
|
|
@ -790,7 +790,6 @@ func testServerWriteTimeout(t *testing.T, mode testMode) {
|
||||||
if err == nil {
|
if err == nil {
|
||||||
t.Errorf("client reading from truncated request body: got nil error, want non-nil")
|
t.Errorf("client reading from truncated request body: got nil error, want non-nil")
|
||||||
}
|
}
|
||||||
cst.close()
|
|
||||||
select {
|
select {
|
||||||
case <-errc:
|
case <-errc:
|
||||||
err = <-errc // io.Copy error
|
err = <-errc // io.Copy error
|
||||||
|
|
@ -801,6 +800,7 @@ func testServerWriteTimeout(t *testing.T, mode testMode) {
|
||||||
default:
|
default:
|
||||||
// The write timeout expired before the handler started.
|
// The write timeout expired before the handler started.
|
||||||
t.Logf("handler didn't run, retrying")
|
t.Logf("handler didn't run, retrying")
|
||||||
|
cst.close()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -194,7 +194,7 @@ func (p *bufferedPipe) Read(b []byte) (int, error) {
|
||||||
if !p.rDeadline.IsZero() {
|
if !p.rDeadline.IsZero() {
|
||||||
d := time.Until(p.rDeadline)
|
d := time.Until(p.rDeadline)
|
||||||
if d <= 0 {
|
if d <= 0 {
|
||||||
return 0, syscall.EAGAIN
|
return 0, os.ErrDeadlineExceeded
|
||||||
}
|
}
|
||||||
time.AfterFunc(d, p.rCond.Broadcast)
|
time.AfterFunc(d, p.rCond.Broadcast)
|
||||||
}
|
}
|
||||||
|
|
@ -221,7 +221,7 @@ func (p *bufferedPipe) Write(b []byte) (int, error) {
|
||||||
if !p.wDeadline.IsZero() {
|
if !p.wDeadline.IsZero() {
|
||||||
d := time.Until(p.wDeadline)
|
d := time.Until(p.wDeadline)
|
||||||
if d <= 0 {
|
if d <= 0 {
|
||||||
return 0, syscall.EAGAIN
|
return 0, os.ErrDeadlineExceeded
|
||||||
}
|
}
|
||||||
time.AfterFunc(d, p.wCond.Broadcast)
|
time.AfterFunc(d, p.wCond.Broadcast)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue