chore: improve testing and increase coverage (#794)
This diff improves testing and increases coverage inside the ./internal/netxlite and ./internal/tracex packages. See https://github.com/ooni/probe/issues/2121
This commit is contained in:
		
							parent
							
								
									464d03184e
								
							
						
					
					
						commit
						d5249a6cf7
					
				| @ -207,23 +207,6 @@ func (state *getaddrinfoState) addrinfoToString(r *C.struct_addrinfo) (string, e | |||||||
| 	} | 	} | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| // staticAddrinfoWithInvalidFamily is an helper to construct an addrinfo struct |  | ||||||
| // that we use in testing. (We cannot call CGO directly from tests.) |  | ||||||
| func staticAddrinfoWithInvalidFamily() *C.struct_addrinfo { |  | ||||||
| 	var value C.struct_addrinfo       // zeroed by Go |  | ||||||
| 	value.ai_socktype = C.SOCK_STREAM // this is what the code expects |  | ||||||
| 	value.ai_family = 0               // but 0 is not AF_INET{,6} |  | ||||||
| 	return &value |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| // staticAddrinfoWithInvalidSocketType is an helper to construct an addrinfo struct |  | ||||||
| // that we use in testing. (We cannot call CGO directly from tests.) |  | ||||||
| func staticAddrinfoWithInvalidSocketType() *C.struct_addrinfo { |  | ||||||
| 	var value C.struct_addrinfo      // zeroed by Go |  | ||||||
| 	value.ai_socktype = C.SOCK_DGRAM // not SOCK_STREAM |  | ||||||
| 	return &value |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| // getaddrinfoCopyIP copies a net.IP. | // getaddrinfoCopyIP copies a net.IP. | ||||||
| // | // | ||||||
| // This function is adapted from copyIP | // This function is adapted from copyIP | ||||||
|  | |||||||
| @ -177,29 +177,29 @@ func NewOOHTTPBaseTransport(dialer model.Dialer, tlsDialer model.TLSDialer) mode | |||||||
| 
 | 
 | ||||||
| 	// Ensure we correctly forward CloseIdleConnections. | 	// Ensure we correctly forward CloseIdleConnections. | ||||||
| 	return &httpTransportConnectionsCloser{ | 	return &httpTransportConnectionsCloser{ | ||||||
| 		HTTPTransport: &stdlibTransport{&oohttp.StdlibTransport{Transport: txp}}, | 		HTTPTransport: &httpTransportStdlib{&oohttp.StdlibTransport{Transport: txp}}, | ||||||
| 		Dialer:        dialer, | 		Dialer:        dialer, | ||||||
| 		TLSDialer:     tlsDialer, | 		TLSDialer:     tlsDialer, | ||||||
| 	} | 	} | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| // stdlibTransport wraps oohttp.StdlibTransport to add .Network() | // stdlibTransport wraps oohttp.StdlibTransport to add .Network() | ||||||
| type stdlibTransport struct { | type httpTransportStdlib struct { | ||||||
| 	StdlibTransport *oohttp.StdlibTransport | 	StdlibTransport *oohttp.StdlibTransport | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| var _ model.HTTPTransport = &stdlibTransport{} | var _ model.HTTPTransport = &httpTransportStdlib{} | ||||||
| 
 | 
 | ||||||
| func (txp *stdlibTransport) CloseIdleConnections() { | func (txp *httpTransportStdlib) CloseIdleConnections() { | ||||||
| 	txp.StdlibTransport.CloseIdleConnections() | 	txp.StdlibTransport.CloseIdleConnections() | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| func (txp *stdlibTransport) RoundTrip(req *http.Request) (*http.Response, error) { | func (txp *httpTransportStdlib) RoundTrip(req *http.Request) (*http.Response, error) { | ||||||
| 	return txp.StdlibTransport.RoundTrip(req) | 	return txp.StdlibTransport.RoundTrip(req) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| // Network implements HTTPTransport.Network. | // Network implements HTTPTransport.Network. | ||||||
| func (txp *stdlibTransport) Network() string { | func (txp *httpTransportStdlib) Network() string { | ||||||
| 	return "tcp" | 	return "tcp" | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | |||||||
| @ -272,7 +272,7 @@ func TestNewHTTPTransport(t *testing.T) { | |||||||
| 		if tlsWithReadTimeout.TLSDialer != td { | 		if tlsWithReadTimeout.TLSDialer != td { | ||||||
| 			t.Fatal("invalid tls dialer") | 			t.Fatal("invalid tls dialer") | ||||||
| 		} | 		} | ||||||
| 		stdlib := connectionsCloser.HTTPTransport.(*stdlibTransport) | 		stdlib := connectionsCloser.HTTPTransport.(*httpTransportStdlib) | ||||||
| 		if !stdlib.StdlibTransport.ForceAttemptHTTP2 { | 		if !stdlib.StdlibTransport.ForceAttemptHTTP2 { | ||||||
| 			t.Fatal("invalid ForceAttemptHTTP2") | 			t.Fatal("invalid ForceAttemptHTTP2") | ||||||
| 		} | 		} | ||||||
| @ -292,6 +292,7 @@ func TestNewHTTPTransport(t *testing.T) { | |||||||
| } | } | ||||||
| 
 | 
 | ||||||
| func TestHTTPDialerWithReadTimeout(t *testing.T) { | func TestHTTPDialerWithReadTimeout(t *testing.T) { | ||||||
|  | 	t.Run("DialContext", func(t *testing.T) { | ||||||
| 		t.Run("on success", func(t *testing.T) { | 		t.Run("on success", func(t *testing.T) { | ||||||
| 			var ( | 			var ( | ||||||
| 				calledWithZeroTime    bool | 				calledWithZeroTime    bool | ||||||
| @ -359,9 +360,11 @@ func TestHTTPDialerWithReadTimeout(t *testing.T) { | |||||||
| 				t.Fatal("expected nil conn here") | 				t.Fatal("expected nil conn here") | ||||||
| 			} | 			} | ||||||
| 		}) | 		}) | ||||||
|  | 	}) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| func TestHTTPTLSDialerWithReadTimeout(t *testing.T) { | func TestHTTPTLSDialerWithReadTimeout(t *testing.T) { | ||||||
|  | 	t.Run("DialContext", func(t *testing.T) { | ||||||
| 		t.Run("on success", func(t *testing.T) { | 		t.Run("on success", func(t *testing.T) { | ||||||
| 			var ( | 			var ( | ||||||
| 				calledWithZeroTime    bool | 				calledWithZeroTime    bool | ||||||
| @ -457,6 +460,7 @@ func TestHTTPTLSDialerWithReadTimeout(t *testing.T) { | |||||||
| 				t.Fatal("not called") | 				t.Fatal("not called") | ||||||
| 			} | 			} | ||||||
| 		}) | 		}) | ||||||
|  | 	}) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| func TestNewHTTPTransportStdlib(t *testing.T) { | func TestNewHTTPTransportStdlib(t *testing.T) { | ||||||
|  | |||||||
| @ -140,7 +140,7 @@ func (d *quicDialerQUICGo) DialContext(ctx context.Context, network string, | |||||||
| 		pconn.Close() // we own it on failure | 		pconn.Close() // we own it on failure | ||||||
| 		return nil, err | 		return nil, err | ||||||
| 	} | 	} | ||||||
| 	return &quicConnectionOwnsConn{EarlyConnection: qconn, conn: pconn}, nil | 	return newQUICConnectionOwnsConn(qconn, pconn), nil | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| func (d *quicDialerQUICGo) dialEarlyContext(ctx context.Context, | func (d *quicDialerQUICGo) dialEarlyContext(ctx context.Context, | ||||||
| @ -183,6 +183,8 @@ type quicDialerHandshakeCompleter struct { | |||||||
| 	Dialer model.QUICDialer | 	Dialer model.QUICDialer | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | var _ model.QUICDialer = &quicDialerHandshakeCompleter{} | ||||||
|  | 
 | ||||||
| // DialContext implements model.QUICDialer.DialContext. | // DialContext implements model.QUICDialer.DialContext. | ||||||
| func (d *quicDialerHandshakeCompleter) DialContext( | func (d *quicDialerHandshakeCompleter) DialContext( | ||||||
| 	ctx context.Context, network, address string, | 	ctx context.Context, network, address string, | ||||||
| @ -214,6 +216,10 @@ type quicConnectionOwnsConn struct { | |||||||
| 	conn model.UDPLikeConn | 	conn model.UDPLikeConn | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | func newQUICConnectionOwnsConn(qconn quic.EarlyConnection, pconn model.UDPLikeConn) *quicConnectionOwnsConn { | ||||||
|  | 	return &quicConnectionOwnsConn{EarlyConnection: qconn, conn: pconn} | ||||||
|  | } | ||||||
|  | 
 | ||||||
| // CloseWithError implements quic.EarlyConnection.CloseWithError. | // CloseWithError implements quic.EarlyConnection.CloseWithError. | ||||||
| func (qconn *quicConnectionOwnsConn) CloseWithError( | func (qconn *quicConnectionOwnsConn) CloseWithError( | ||||||
| 	code quic.ApplicationErrorCode, reason string) error { | 	code quic.ApplicationErrorCode, reason string) error { | ||||||
|  | |||||||
| @ -302,6 +302,31 @@ func TestQUICDialerQUICGo(t *testing.T) { | |||||||
| 				t.Fatal("the ServerName field must match") | 				t.Fatal("the ServerName field must match") | ||||||
| 			} | 			} | ||||||
| 		}) | 		}) | ||||||
|  | 
 | ||||||
|  | 		t.Run("returns a quicDialerOwnConn in case of success", func(t *testing.T) { | ||||||
|  | 			tlsConfig := &tls.Config{ | ||||||
|  | 				ServerName: "dns.google", | ||||||
|  | 			} | ||||||
|  | 			fakeconn := &mocks.QUICEarlyConnection{} | ||||||
|  | 			systemdialer := quicDialerQUICGo{ | ||||||
|  | 				QUICListener: &quicListenerStdlib{}, | ||||||
|  | 				mockDialEarlyContext: func(ctx context.Context, pconn net.PacketConn, | ||||||
|  | 					remoteAddr net.Addr, host string, tlsConfig *tls.Config, | ||||||
|  | 					quicConfig *quic.Config) (quic.EarlyConnection, error) { | ||||||
|  | 					return fakeconn, nil | ||||||
|  | 				}, | ||||||
|  | 			} | ||||||
|  | 			ctx := context.Background() | ||||||
|  | 			qconn, err := systemdialer.DialContext( | ||||||
|  | 				ctx, "udp", "8.8.8.8:443", tlsConfig, &quic.Config{}) | ||||||
|  | 			if err != nil { | ||||||
|  | 				t.Fatal(err) | ||||||
|  | 			} | ||||||
|  | 			connOwner := qconn.(*quicConnectionOwnsConn) | ||||||
|  | 			if connOwner.EarlyConnection != fakeconn { | ||||||
|  | 				t.Fatal("invalid underlying conn") | ||||||
|  | 			} | ||||||
|  | 		}) | ||||||
| 	}) | 	}) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| @ -406,6 +431,33 @@ func TestQUICDialerHandshakeCompleter(t *testing.T) { | |||||||
| 	}) | 	}) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | func TestQUICConnectionOwnsConn(t *testing.T) { | ||||||
|  | 	var ( | ||||||
|  | 		quicClose bool | ||||||
|  | 		udpClose  bool | ||||||
|  | 	) | ||||||
|  | 	qconn := &mocks.QUICEarlyConnection{ | ||||||
|  | 		MockCloseWithError: func(code quic.ApplicationErrorCode, reason string) error { | ||||||
|  | 			quicClose = true | ||||||
|  | 			return nil | ||||||
|  | 		}, | ||||||
|  | 	} | ||||||
|  | 	pconn := &mocks.UDPLikeConn{ | ||||||
|  | 		MockClose: func() error { | ||||||
|  | 			udpClose = true | ||||||
|  | 			return nil | ||||||
|  | 		}, | ||||||
|  | 	} | ||||||
|  | 	conn := newQUICConnectionOwnsConn(qconn, pconn) | ||||||
|  | 	conn.CloseWithError(0, "") | ||||||
|  | 	if !quicClose { | ||||||
|  | 		t.Fatal("did not call qconn.CloseWithError") | ||||||
|  | 	} | ||||||
|  | 	if !udpClose { | ||||||
|  | 		t.Fatal("did not call pconn.Close") | ||||||
|  | 	} | ||||||
|  | } | ||||||
|  | 
 | ||||||
| func TestQUICDialerResolver(t *testing.T) { | func TestQUICDialerResolver(t *testing.T) { | ||||||
| 	t.Run("CloseIdleConnections", func(t *testing.T) { | 	t.Run("CloseIdleConnections", func(t *testing.T) { | ||||||
| 		var ( | 		var ( | ||||||
| @ -518,6 +570,27 @@ func TestQUICDialerResolver(t *testing.T) { | |||||||
| 				t.Fatal("gotTLSConfig.ServerName has not been set") | 				t.Fatal("gotTLSConfig.ServerName has not been set") | ||||||
| 			} | 			} | ||||||
| 		}) | 		}) | ||||||
|  | 
 | ||||||
|  | 		t.Run("on success", func(t *testing.T) { | ||||||
|  | 			expectedQConn := &mocks.QUICEarlyConnection{} | ||||||
|  | 			dialer := &quicDialerResolver{ | ||||||
|  | 				Resolver: NewResolverStdlib(log.Log), | ||||||
|  | 				Dialer: &mocks.QUICDialer{ | ||||||
|  | 					MockDialContext: func(ctx context.Context, network, address string, | ||||||
|  | 						tlsConfig *tls.Config, quicConfig *quic.Config) (quic.EarlyConnection, error) { | ||||||
|  | 						return expectedQConn, nil | ||||||
|  | 					}, | ||||||
|  | 				}} | ||||||
|  | 			qconn, err := dialer.DialContext( | ||||||
|  | 				context.Background(), "udp", "8.8.4.4:443", | ||||||
|  | 				&tls.Config{}, &quic.Config{}) | ||||||
|  | 			if err != nil { | ||||||
|  | 				t.Fatal(err) | ||||||
|  | 			} | ||||||
|  | 			if qconn != expectedQConn { | ||||||
|  | 				t.Fatal("unexpected underlying qconn") | ||||||
|  | 			} | ||||||
|  | 		}) | ||||||
| 	}) | 	}) | ||||||
| 
 | 
 | ||||||
| 	t.Run("lookup host with address", func(t *testing.T) { | 	t.Run("lookup host with address", func(t *testing.T) { | ||||||
|  | |||||||
| @ -22,6 +22,8 @@ type ParallelResolver struct { | |||||||
| 	Txp model.DNSTransport | 	Txp model.DNSTransport | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | var _ model.Resolver = &ParallelResolver{} | ||||||
|  | 
 | ||||||
| // UnwrappedParallelResolver creates a new ParallelResolver instance. This instance is | // UnwrappedParallelResolver creates a new ParallelResolver instance. This instance is | ||||||
| // not wrapped and you should wrap if before using it. | // not wrapped and you should wrap if before using it. | ||||||
| func NewUnwrappedParallelResolver(t model.DNSTransport) *ParallelResolver { | func NewUnwrappedParallelResolver(t model.DNSTransport) *ParallelResolver { | ||||||
|  | |||||||
| @ -33,6 +33,8 @@ type SerialResolver struct { | |||||||
| 	Txp model.DNSTransport | 	Txp model.DNSTransport | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | var _ model.Resolver = &SerialResolver{} | ||||||
|  | 
 | ||||||
| // NewUnwrappedSerialResolver creates a new, and unwrapped, SerialResolver instance. | // NewUnwrappedSerialResolver creates a new, and unwrapped, SerialResolver instance. | ||||||
| func NewUnwrappedSerialResolver(t model.DNSTransport) *SerialResolver { | func NewUnwrappedSerialResolver(t model.DNSTransport) *SerialResolver { | ||||||
| 	return &SerialResolver{ | 	return &SerialResolver{ | ||||||
|  | |||||||
							
								
								
									
										36
									
								
								internal/tracex/event_test.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										36
									
								
								internal/tracex/event_test.go
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,36 @@ | |||||||
|  | package tracex | ||||||
|  | 
 | ||||||
|  | import "testing" | ||||||
|  | 
 | ||||||
|  | func TestUnusedEventsNames(t *testing.T) { | ||||||
|  | 	// Tests that we don't break the names of events we're currently | ||||||
|  | 	// not getting the name of directly even if they're saved. | ||||||
|  | 
 | ||||||
|  | 	t.Run("EventQUICHandshakeStart", func(t *testing.T) { | ||||||
|  | 		ev := &EventQUICHandshakeStart{} | ||||||
|  | 		if ev.Name() != "quic_handshake_start" { | ||||||
|  | 			t.Fatal("invalid event name") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("EventQUICHandshakeDone", func(t *testing.T) { | ||||||
|  | 		ev := &EventQUICHandshakeDone{} | ||||||
|  | 		if ev.Name() != "quic_handshake_done" { | ||||||
|  | 			t.Fatal("invalid event name") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("EventTLSHandshakeStart", func(t *testing.T) { | ||||||
|  | 		ev := &EventTLSHandshakeStart{} | ||||||
|  | 		if ev.Name() != "tls_handshake_start" { | ||||||
|  | 			t.Fatal("invalid event name") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("EventTLSHandshakeDone", func(t *testing.T) { | ||||||
|  | 		ev := &EventTLSHandshakeDone{} | ||||||
|  | 		if ev.Name() != "tls_handshake_done" { | ||||||
|  | 			t.Fatal("invalid event name") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | } | ||||||
| @ -177,6 +177,14 @@ func TestQUICDialerSaver(t *testing.T) { | |||||||
| 	}) | 	}) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | func TestWrapQUICListener(t *testing.T) { | ||||||
|  | 	var saver *Saver | ||||||
|  | 	ql := &mocks.QUICListener{} | ||||||
|  | 	if saver.WrapQUICListener(ql) != ql { | ||||||
|  | 		t.Fatal("unexpected result") | ||||||
|  | 	} | ||||||
|  | } | ||||||
|  | 
 | ||||||
| func TestQUICListenerSaver(t *testing.T) { | func TestQUICListenerSaver(t *testing.T) { | ||||||
| 	t.Run("on failure", func(t *testing.T) { | 	t.Run("on failure", func(t *testing.T) { | ||||||
| 		expected := errors.New("mocked error") | 		expected := errors.New("mocked error") | ||||||
|  | |||||||
| @ -15,7 +15,16 @@ import ( | |||||||
| 	"github.com/ooni/probe-cli/v3/internal/runtimex" | 	"github.com/ooni/probe-cli/v3/internal/runtimex" | ||||||
| ) | ) | ||||||
| 
 | 
 | ||||||
|  | func TestWrapResolver(t *testing.T) { | ||||||
|  | 	var saver *Saver | ||||||
|  | 	reso := &mocks.Resolver{} | ||||||
|  | 	if saver.WrapResolver(reso) != reso { | ||||||
|  | 		t.Fatal("unexpected result") | ||||||
|  | 	} | ||||||
|  | } | ||||||
|  | 
 | ||||||
| func TestResolverSaver(t *testing.T) { | func TestResolverSaver(t *testing.T) { | ||||||
|  | 	t.Run("LookupHost", func(t *testing.T) { | ||||||
| 		t.Run("on failure", func(t *testing.T) { | 		t.Run("on failure", func(t *testing.T) { | ||||||
| 			expected := netxlite.ErrOODNSNoSuchHost | 			expected := netxlite.ErrOODNSNoSuchHost | ||||||
| 			saver := &Saver{} | 			saver := &Saver{} | ||||||
| @ -103,9 +112,96 @@ func TestResolverSaver(t *testing.T) { | |||||||
| 				t.Fatal("the saved time is wrong") | 				t.Fatal("the saved time is wrong") | ||||||
| 			} | 			} | ||||||
| 		}) | 		}) | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("Network", func(t *testing.T) { | ||||||
|  | 		saver := &Saver{} | ||||||
|  | 		child := &mocks.Resolver{ | ||||||
|  | 			MockNetwork: func() string { | ||||||
|  | 				return "x" | ||||||
|  | 			}, | ||||||
|  | 		} | ||||||
|  | 		reso := saver.WrapResolver(child) | ||||||
|  | 		if reso.Network() != "x" { | ||||||
|  | 			t.Fatal("unexpected result") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("Address", func(t *testing.T) { | ||||||
|  | 		saver := &Saver{} | ||||||
|  | 		child := &mocks.Resolver{ | ||||||
|  | 			MockAddress: func() string { | ||||||
|  | 				return "x" | ||||||
|  | 			}, | ||||||
|  | 		} | ||||||
|  | 		reso := saver.WrapResolver(child) | ||||||
|  | 		if reso.Address() != "x" { | ||||||
|  | 			t.Fatal("unexpected result") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("LookupHTTPS", func(t *testing.T) { | ||||||
|  | 		expected := errors.New("mocked") | ||||||
|  | 		saver := &Saver{} | ||||||
|  | 		child := &mocks.Resolver{ | ||||||
|  | 			MockLookupHTTPS: func(ctx context.Context, domain string) (*model.HTTPSSvc, error) { | ||||||
|  | 				return nil, expected | ||||||
|  | 			}, | ||||||
|  | 		} | ||||||
|  | 		reso := saver.WrapResolver(child) | ||||||
|  | 		https, err := reso.LookupHTTPS(context.Background(), "dns.google") | ||||||
|  | 		if !errors.Is(err, expected) { | ||||||
|  | 			t.Fatal("unexpected err", err) | ||||||
|  | 		} | ||||||
|  | 		if https != nil { | ||||||
|  | 			t.Fatal("expected nil") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("LookupNS", func(t *testing.T) { | ||||||
|  | 		expected := errors.New("mocked") | ||||||
|  | 		saver := &Saver{} | ||||||
|  | 		child := &mocks.Resolver{ | ||||||
|  | 			MockLookupNS: func(ctx context.Context, domain string) ([]*net.NS, error) { | ||||||
|  | 				return nil, expected | ||||||
|  | 			}, | ||||||
|  | 		} | ||||||
|  | 		reso := saver.WrapResolver(child) | ||||||
|  | 		ns, err := reso.LookupNS(context.Background(), "dns.google") | ||||||
|  | 		if !errors.Is(err, expected) { | ||||||
|  | 			t.Fatal("unexpected err", err) | ||||||
|  | 		} | ||||||
|  | 		if len(ns) != 0 { | ||||||
|  | 			t.Fatal("expected zero length array") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("CloseIdleConnections", func(t *testing.T) { | ||||||
|  | 		var called bool | ||||||
|  | 		saver := &Saver{} | ||||||
|  | 		child := &mocks.Resolver{ | ||||||
|  | 			MockCloseIdleConnections: func() { | ||||||
|  | 				called = true | ||||||
|  | 			}, | ||||||
|  | 		} | ||||||
|  | 		reso := saver.WrapResolver(child) | ||||||
|  | 		reso.CloseIdleConnections() | ||||||
|  | 		if !called { | ||||||
|  | 			t.Fatal("not called") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | func TestWrapDNSTransport(t *testing.T) { | ||||||
|  | 	var saver *Saver | ||||||
|  | 	txp := &mocks.DNSTransport{} | ||||||
|  | 	if saver.WrapDNSTransport(txp) != txp { | ||||||
|  | 		t.Fatal("unexpected result") | ||||||
|  | 	} | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| func TestDNSTransportSaver(t *testing.T) { | func TestDNSTransportSaver(t *testing.T) { | ||||||
|  | 	t.Run("RoundTrip", func(t *testing.T) { | ||||||
| 		t.Run("on failure", func(t *testing.T) { | 		t.Run("on failure", func(t *testing.T) { | ||||||
| 			expected := netxlite.ErrOODNSNoSuchHost | 			expected := netxlite.ErrOODNSNoSuchHost | ||||||
| 			saver := &Saver{} | 			saver := &Saver{} | ||||||
| @ -230,6 +326,61 @@ func TestDNSTransportSaver(t *testing.T) { | |||||||
| 				t.Fatal("the saved time is wrong") | 				t.Fatal("the saved time is wrong") | ||||||
| 			} | 			} | ||||||
| 		}) | 		}) | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("Network", func(t *testing.T) { | ||||||
|  | 		saver := &Saver{} | ||||||
|  | 		child := &mocks.DNSTransport{ | ||||||
|  | 			MockNetwork: func() string { | ||||||
|  | 				return "x" | ||||||
|  | 			}, | ||||||
|  | 		} | ||||||
|  | 		txp := saver.WrapDNSTransport(child) | ||||||
|  | 		if txp.Network() != "x" { | ||||||
|  | 			t.Fatal("unexpected result") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("Address", func(t *testing.T) { | ||||||
|  | 		saver := &Saver{} | ||||||
|  | 		child := &mocks.DNSTransport{ | ||||||
|  | 			MockAddress: func() string { | ||||||
|  | 				return "x" | ||||||
|  | 			}, | ||||||
|  | 		} | ||||||
|  | 		txp := saver.WrapDNSTransport(child) | ||||||
|  | 		if txp.Address() != "x" { | ||||||
|  | 			t.Fatal("unexpected result") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("CloseIdleConnections", func(t *testing.T) { | ||||||
|  | 		var called bool | ||||||
|  | 		saver := &Saver{} | ||||||
|  | 		child := &mocks.DNSTransport{ | ||||||
|  | 			MockCloseIdleConnections: func() { | ||||||
|  | 				called = true | ||||||
|  | 			}, | ||||||
|  | 		} | ||||||
|  | 		txp := saver.WrapDNSTransport(child) | ||||||
|  | 		txp.CloseIdleConnections() | ||||||
|  | 		if !called { | ||||||
|  | 			t.Fatal("not called") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 
 | ||||||
|  | 	t.Run("RequiresPadding", func(t *testing.T) { | ||||||
|  | 		saver := &Saver{} | ||||||
|  | 		child := &mocks.DNSTransport{ | ||||||
|  | 			MockRequiresPadding: func() bool { | ||||||
|  | 				return true | ||||||
|  | 			}, | ||||||
|  | 		} | ||||||
|  | 		txp := saver.WrapDNSTransport(child) | ||||||
|  | 		if !txp.RequiresPadding() { | ||||||
|  | 			t.Fatal("unexpected result") | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| func newFakeResolverWithExplicitError(err error) model.Resolver { | func newFakeResolverWithExplicitError(err error) model.Resolver { | ||||||
|  | |||||||
| @ -12,6 +12,14 @@ import ( | |||||||
| 	"github.com/ooni/probe-cli/v3/internal/model/mocks" | 	"github.com/ooni/probe-cli/v3/internal/model/mocks" | ||||||
| ) | ) | ||||||
| 
 | 
 | ||||||
|  | func TestWrapTLSHandshaker(t *testing.T) { | ||||||
|  | 	var saver *Saver | ||||||
|  | 	thx := &mocks.TLSHandshaker{} | ||||||
|  | 	if saver.WrapTLSHandshaker(thx) != thx { | ||||||
|  | 		t.Fatal("unexpected result") | ||||||
|  | 	} | ||||||
|  | } | ||||||
|  | 
 | ||||||
| func TestTLSHandshakerSaver(t *testing.T) { | func TestTLSHandshakerSaver(t *testing.T) { | ||||||
| 
 | 
 | ||||||
| 	t.Run("Handshake", func(t *testing.T) { | 	t.Run("Handshake", func(t *testing.T) { | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user