forked from quic-go/quic-go
@@ -1,8 +1,6 @@
|
||||
package http3
|
||||
|
||||
import (
|
||||
"io"
|
||||
"net/http"
|
||||
"os"
|
||||
"strconv"
|
||||
"testing"
|
||||
@@ -18,14 +16,6 @@ func TestHttp3(t *testing.T) {
|
||||
RunSpecs(t, "HTTP/3 Suite")
|
||||
}
|
||||
|
||||
func mustNewRequest(method, url string, body io.Reader) *http.Request {
|
||||
req, err := http.NewRequest(method, url, body)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return req
|
||||
}
|
||||
|
||||
var mockCtrl *gomock.Controller
|
||||
|
||||
var _ = BeforeEach(func() {
|
||||
|
||||
@@ -4,6 +4,7 @@ import (
|
||||
"bytes"
|
||||
"io"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"testing"
|
||||
|
||||
"github.com/quic-go/qpack"
|
||||
@@ -41,8 +42,7 @@ func TestRequestWriterGetRequestGzip(t *testing.T) {
|
||||
}
|
||||
|
||||
func testRequestWriterGzip(t *testing.T, gzip bool) {
|
||||
req, err := http.NewRequest(http.MethodGet, "https://quic-go.net/index.html?foo=bar", nil)
|
||||
require.NoError(t, err)
|
||||
req := httptest.NewRequest(http.MethodGet, "https://quic-go.net/index.html?foo=bar", nil)
|
||||
req.AddCookie(&http.Cookie{Name: "foo", Value: "bar"})
|
||||
req.AddCookie(&http.Cookie{Name: "baz", Value: "lorem ipsum"})
|
||||
|
||||
@@ -64,8 +64,7 @@ func testRequestWriterGzip(t *testing.T, gzip bool) {
|
||||
}
|
||||
|
||||
func TestRequestWriterInvalidHostHeader(t *testing.T) {
|
||||
req, err := http.NewRequest(http.MethodGet, "https://quic-go.net/index.html?foo=bar", nil)
|
||||
require.NoError(t, err)
|
||||
req := httptest.NewRequest(http.MethodGet, "https://quic-go.net/index.html?foo=bar", nil)
|
||||
req.Host = "foo@bar" // @ is invalid
|
||||
rw := newRequestWriter()
|
||||
require.EqualError(t,
|
||||
@@ -75,6 +74,7 @@ func TestRequestWriterInvalidHostHeader(t *testing.T) {
|
||||
}
|
||||
|
||||
func TestRequestWriterConnect(t *testing.T) {
|
||||
// httptest.NewRequest does not properly support the CONNECT method
|
||||
req, err := http.NewRequest(http.MethodConnect, "https://quic-go.net/", nil)
|
||||
require.NoError(t, err)
|
||||
rw := newRequestWriter()
|
||||
@@ -89,6 +89,7 @@ func TestRequestWriterConnect(t *testing.T) {
|
||||
}
|
||||
|
||||
func TestRequestWriterExtendedConnect(t *testing.T) {
|
||||
// httptest.NewRequest does not properly support the CONNECT method
|
||||
req, err := http.NewRequest(http.MethodConnect, "https://quic-go.net/", nil)
|
||||
require.NoError(t, err)
|
||||
req.Proto = "webtransport"
|
||||
|
||||
@@ -7,6 +7,7 @@ import (
|
||||
"errors"
|
||||
"io"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
@@ -57,13 +58,13 @@ func TestRequestValidation(t *testing.T) {
|
||||
}{
|
||||
{
|
||||
name: "plain HTTP",
|
||||
req: mustNewRequest(http.MethodGet, "http://www.example.org/", nil),
|
||||
req: httptest.NewRequest(http.MethodGet, "http://www.example.org/", nil),
|
||||
expectedErr: "http3: unsupported protocol scheme: http",
|
||||
},
|
||||
{
|
||||
name: "missing URL",
|
||||
req: func() *http.Request {
|
||||
r := mustNewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r := httptest.NewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r.URL = nil
|
||||
return r
|
||||
}(),
|
||||
@@ -72,7 +73,7 @@ func TestRequestValidation(t *testing.T) {
|
||||
{
|
||||
name: "missing URL Host",
|
||||
req: func() *http.Request {
|
||||
r := mustNewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r := httptest.NewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r.URL.Host = ""
|
||||
return r
|
||||
}(),
|
||||
@@ -81,7 +82,7 @@ func TestRequestValidation(t *testing.T) {
|
||||
{
|
||||
name: "missing header",
|
||||
req: func() *http.Request {
|
||||
r := mustNewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r := httptest.NewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r.Header = nil
|
||||
return r
|
||||
}(),
|
||||
@@ -90,7 +91,7 @@ func TestRequestValidation(t *testing.T) {
|
||||
{
|
||||
name: "invalid header name",
|
||||
req: func() *http.Request {
|
||||
r := mustNewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r := httptest.NewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r.Header.Add("foobär", "value")
|
||||
return r
|
||||
}(),
|
||||
@@ -99,7 +100,7 @@ func TestRequestValidation(t *testing.T) {
|
||||
{
|
||||
name: "invalid header value",
|
||||
req: func() *http.Request {
|
||||
r := mustNewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r := httptest.NewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r.Header.Add("foo", string([]byte{0x7}))
|
||||
return r
|
||||
}(),
|
||||
@@ -108,7 +109,7 @@ func TestRequestValidation(t *testing.T) {
|
||||
{
|
||||
name: "invalid method",
|
||||
req: func() *http.Request {
|
||||
r := mustNewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r := httptest.NewRequest(http.MethodGet, "https://www.example.org/", nil)
|
||||
r.Method = "foobär"
|
||||
return r
|
||||
}(),
|
||||
@@ -147,7 +148,7 @@ func TestTransportDialHostname(t *testing.T) {
|
||||
}
|
||||
|
||||
t.Run("port set", func(t *testing.T) {
|
||||
req := mustNewRequest(http.MethodGet, "https://quic-go.net:1234", nil)
|
||||
req := httptest.NewRequest(http.MethodGet, "https://quic-go.net:1234", nil)
|
||||
_, err := tr.RoundTripOpt(req, RoundTripOpt{})
|
||||
require.EqualError(t, err, "test done")
|
||||
select {
|
||||
@@ -161,7 +162,7 @@ func TestTransportDialHostname(t *testing.T) {
|
||||
|
||||
// if the request doesn't have a port, the default port is used
|
||||
t.Run("port not set", func(t *testing.T) {
|
||||
req := mustNewRequest(http.MethodGet, "https://quic-go.net", nil)
|
||||
req := httptest.NewRequest(http.MethodGet, "https://quic-go.net", nil)
|
||||
_, err := tr.RoundTripOpt(req, RoundTripOpt{})
|
||||
require.EqualError(t, err, "test done")
|
||||
select {
|
||||
@@ -184,7 +185,7 @@ func TestTransportDatagrams(t *testing.T) {
|
||||
return nil, assert.AnError
|
||||
},
|
||||
}
|
||||
req := mustNewRequest(http.MethodGet, "https://example.com", nil)
|
||||
req := httptest.NewRequest(http.MethodGet, "https://example.com", nil)
|
||||
_, err := tr.RoundTripOpt(req, RoundTripOpt{})
|
||||
require.ErrorIs(t, err, assert.AnError)
|
||||
})
|
||||
@@ -199,7 +200,7 @@ func TestTransportDatagrams(t *testing.T) {
|
||||
return nil, nil
|
||||
},
|
||||
}
|
||||
req := mustNewRequest(http.MethodGet, "https://example.com", nil)
|
||||
req := httptest.NewRequest(http.MethodGet, "https://example.com", nil)
|
||||
_, err := tr.RoundTripOpt(req, RoundTripOpt{})
|
||||
require.EqualError(t, err, "HTTP Datagrams enabled, but QUIC Datagrams disabled")
|
||||
})
|
||||
@@ -210,7 +211,7 @@ func TestTransportMultipleQUICVersions(t *testing.T) {
|
||||
Versions: []quic.Version{protocol.Version2, protocol.Version1},
|
||||
}
|
||||
tr := &Transport{QUICConfig: qconf}
|
||||
req := mustNewRequest(http.MethodGet, "https://example.com", nil)
|
||||
req := httptest.NewRequest(http.MethodGet, "https://example.com", nil)
|
||||
_, err := tr.RoundTrip(req)
|
||||
require.EqualError(t, err, "can only use a single QUIC version for dialing a HTTP/3 connection")
|
||||
}
|
||||
@@ -231,7 +232,7 @@ func TestTransportConnectionReuse(t *testing.T) {
|
||||
newClientConn: func(quic.EarlyConnection) clientConn { return cl },
|
||||
}
|
||||
|
||||
req1 := mustNewRequest("GET", "https://quic-go.net/file1.html", nil)
|
||||
req1 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file1.html", nil)
|
||||
// if OnlyCachedConn is set, no connection is dialed
|
||||
_, err := tr.RoundTripOpt(req1, RoundTripOpt{OnlyCachedConn: true})
|
||||
require.ErrorIs(t, err, ErrNoCachedConn)
|
||||
@@ -245,7 +246,7 @@ func TestTransportConnectionReuse(t *testing.T) {
|
||||
require.Equal(t, 1, dialCount)
|
||||
|
||||
// ... which is then used for the second request
|
||||
req2 := mustNewRequest("GET", "https://quic-go.net/file2.html", nil)
|
||||
req2 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file2.html", nil)
|
||||
cl.EXPECT().RoundTrip(req2).Return(&http.Response{Request: req2}, nil)
|
||||
rsp, err = tr.RoundTrip(req2)
|
||||
require.NoError(t, err)
|
||||
@@ -294,7 +295,7 @@ func testTransportConnectionRedial(t *testing.T, connClosed bool, roundtripErr,
|
||||
}
|
||||
|
||||
// the first request succeeds
|
||||
req1 := mustNewRequest("GET", "https://quic-go.net/file1.html", nil)
|
||||
req1 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file1.html", nil)
|
||||
cl.EXPECT().RoundTrip(req1).Return(&http.Response{Request: req1}, nil)
|
||||
rsp, err := tr.RoundTrip(req1)
|
||||
require.NoError(t, err)
|
||||
@@ -302,7 +303,7 @@ func testTransportConnectionRedial(t *testing.T, connClosed bool, roundtripErr,
|
||||
require.Equal(t, 1, dialCount)
|
||||
|
||||
// the second request reuses the QUIC connection, and encounters an error
|
||||
req2 := mustNewRequest("GET", "https://quic-go.net/file2.html", nil)
|
||||
req2 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file2.html", nil)
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
if connClosed {
|
||||
@@ -328,7 +329,7 @@ func testTransportConnectionRedial(t *testing.T, connClosed bool, roundtripErr,
|
||||
return
|
||||
}
|
||||
currentDialCount := dialCount
|
||||
req3 := mustNewRequest("GET", "https://quic-go.net/file3.html", nil)
|
||||
req3 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file3.html", nil)
|
||||
cl.EXPECT().RoundTrip(req3).Return(&http.Response{Request: req3}, nil)
|
||||
rsp, err = tr.RoundTrip(req3)
|
||||
require.NoError(t, err)
|
||||
@@ -353,7 +354,7 @@ func TestTransportRequestContextCancellation(t *testing.T) {
|
||||
}
|
||||
|
||||
// the first request succeeds
|
||||
req1 := mustNewRequest("GET", "https://quic-go.net/file1.html", nil)
|
||||
req1 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file1.html", nil)
|
||||
cl.EXPECT().RoundTrip(req1).Return(&http.Response{Request: req1}, nil)
|
||||
rsp, err := tr.RoundTrip(req1)
|
||||
require.NoError(t, err)
|
||||
@@ -361,7 +362,7 @@ func TestTransportRequestContextCancellation(t *testing.T) {
|
||||
require.Equal(t, 1, dialCount)
|
||||
|
||||
// the second request reuses the QUIC connection, and runs into the cancelled context
|
||||
req2 := mustNewRequest("GET", "https://quic-go.net/file2.html", nil)
|
||||
req2 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file2.html", nil)
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
req2 = req2.WithContext(ctx)
|
||||
cl.EXPECT().RoundTrip(req2).DoAndReturn(
|
||||
@@ -375,7 +376,7 @@ func TestTransportRequestContextCancellation(t *testing.T) {
|
||||
require.Equal(t, 1, dialCount)
|
||||
|
||||
// the next request reuses the QUIC connection
|
||||
req3 := mustNewRequest("GET", "https://quic-go.net/file2.html", nil)
|
||||
req3 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file2.html", nil)
|
||||
cl.EXPECT().RoundTrip(req3).Return(&http.Response{Request: req3}, nil)
|
||||
rsp, err = tr.RoundTrip(req3)
|
||||
require.NoError(t, err)
|
||||
@@ -402,12 +403,12 @@ func TestTransportConnetionRedialHandshakeError(t *testing.T) {
|
||||
newClientConn: func(quic.EarlyConnection) clientConn { return cl },
|
||||
}
|
||||
|
||||
req1 := mustNewRequest("GET", "https://quic-go.net/file1.html", nil)
|
||||
req1 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file1.html", nil)
|
||||
_, err := tr.RoundTrip(req1)
|
||||
require.ErrorIs(t, err, assert.AnError)
|
||||
require.Equal(t, 1, dialCount)
|
||||
|
||||
req2 := mustNewRequest("GET", "https://quic-go.net/file2.html", nil)
|
||||
req2 := httptest.NewRequest(http.MethodGet, "https://quic-go.net/file2.html", nil)
|
||||
cl.EXPECT().RoundTrip(req2).Return(&http.Response{Request: req2}, nil)
|
||||
rsp, err := tr.RoundTrip(req2)
|
||||
require.NoError(t, err)
|
||||
@@ -428,7 +429,7 @@ func TestTransportCloseEstablishedConnections(t *testing.T) {
|
||||
return cl
|
||||
},
|
||||
}
|
||||
req := mustNewRequest(http.MethodGet, "https://quic-go.net/foobar.html", nil)
|
||||
req := httptest.NewRequest(http.MethodGet, "https://quic-go.net/foobar.html", nil)
|
||||
_, err := tr.RoundTrip(req)
|
||||
require.NoError(t, err)
|
||||
conn.EXPECT().CloseWithError(quic.ApplicationErrorCode(0), "")
|
||||
@@ -448,7 +449,7 @@ func TestTransportCloseInFlightDials(t *testing.T) {
|
||||
return nil, err
|
||||
},
|
||||
}
|
||||
req := mustNewRequest(http.MethodGet, "https://quic-go.net/foobar.html", nil)
|
||||
req := httptest.NewRequest(http.MethodGet, "https://quic-go.net/foobar.html", nil)
|
||||
|
||||
errChan := make(chan error, 1)
|
||||
go func() {
|
||||
@@ -498,8 +499,8 @@ func TestTransportCloseIdleConnections(t *testing.T) {
|
||||
return cl
|
||||
},
|
||||
}
|
||||
req1 := mustNewRequest(http.MethodGet, "https://site1.com", nil)
|
||||
req2 := mustNewRequest(http.MethodGet, "https://site2.com", nil)
|
||||
req1 := httptest.NewRequest(http.MethodGet, "https://site1.com", nil)
|
||||
req2 := httptest.NewRequest(http.MethodGet, "https://site2.com", nil)
|
||||
require.NotEqual(t, req1.Host, req2.Host)
|
||||
ctx1, cancel1 := context.WithCancel(context.Background())
|
||||
ctx2, cancel2 := context.WithCancel(context.Background())
|
||||
|
||||
Reference in New Issue
Block a user