github.com/yandex/pandora@v0.5.32/lib/netutil/netutil_test.go (about)

     1  package netutil
     2  
     3  import (
     4  	"context"
     5  	"net"
     6  	"strconv"
     7  	"testing"
     8  	"time"
     9  
    10  	"github.com/pkg/errors"
    11  	"github.com/stretchr/testify/assert"
    12  	netmock "github.com/yandex/pandora/lib/netutil/mocks"
    13  )
    14  
    15  func Test_DNS(t *testing.T) {
    16  	t.Run("lookup reachable", func(t *testing.T) {
    17  		listener, err := net.ListenTCP("tcp4", nil)
    18  		defer func() { _ = listener.Close() }()
    19  		assert.NoError(t, err)
    20  
    21  		port := strconv.Itoa(listener.Addr().(*net.TCPAddr).Port)
    22  		addr := "localhost:" + port
    23  		expectedResolved := "127.0.0.1:" + port
    24  
    25  		resolved, err := LookupReachable(addr, time.Second)
    26  		assert.NoError(t, err)
    27  		assert.Equal(t, expectedResolved, resolved)
    28  	})
    29  
    30  	const (
    31  		addr     = "localhost:8888"
    32  		resolved = "[::1]:8888"
    33  	)
    34  
    35  	t.Run("cache", func(t *testing.T) {
    36  		cache := &SimpleDNSCache{}
    37  		got, ok := cache.Get(addr)
    38  		assert.False(t, ok)
    39  		assert.Equal(t, "", got)
    40  
    41  		cache.Add(addr, resolved)
    42  		got, ok = cache.Get(addr)
    43  		assert.True(t, ok)
    44  		assert.Equal(t, resolved, got)
    45  	})
    46  
    47  	t.Run("Dialer cache miss", func(t *testing.T) {
    48  		ctx := context.Background()
    49  		mockConn := &netmock.Conn{}
    50  		mockConn.On("RemoteAddr").Return(&net.TCPAddr{
    51  			IP:   net.IPv6loopback,
    52  			Port: 8888,
    53  		})
    54  		cache := &netmock.DNSCache{}
    55  		cache.On("Get", addr).Return("", false)
    56  		cache.On("Add", addr, resolved)
    57  		dialer := &netmock.Dialer{}
    58  		dialer.On("DialContext", ctx, "tcp", addr).Return(mockConn, nil)
    59  
    60  		testee := NewDNSCachingDialer(dialer, cache)
    61  		conn, err := testee.DialContext(ctx, "tcp", addr)
    62  		assert.NoError(t, err)
    63  		assert.Equal(t, mockConn, conn)
    64  
    65  		mockConn.AssertExpectations(t)
    66  		cache.AssertExpectations(t)
    67  		dialer.AssertExpectations(t)
    68  	})
    69  
    70  	t.Run("Dialer cache hit", func(t *testing.T) {
    71  		ctx := context.Background()
    72  		mockConn := &netmock.Conn{}
    73  		cache := &netmock.DNSCache{}
    74  		cache.On("Get", addr).Return(resolved, true)
    75  		dialer := &netmock.Dialer{}
    76  		dialer.On("DialContext", ctx, "tcp", resolved).Return(mockConn, nil)
    77  
    78  		testee := NewDNSCachingDialer(dialer, cache)
    79  		conn, err := testee.DialContext(ctx, "tcp", addr)
    80  		assert.NoError(t, err)
    81  		assert.Equal(t, mockConn, conn)
    82  
    83  		mockConn.AssertExpectations(t)
    84  		cache.AssertExpectations(t)
    85  		dialer.AssertExpectations(t)
    86  	})
    87  
    88  	t.Run("Dialer cache miss err", func(t *testing.T) {
    89  		ctx := context.Background()
    90  		expectedErr := errors.New("dial failed")
    91  		cache := &netmock.DNSCache{}
    92  		cache.On("Get", addr).Return("", false)
    93  		dialer := &netmock.Dialer{}
    94  		dialer.On("DialContext", ctx, "tcp", addr).Return(nil, expectedErr)
    95  
    96  		testee := NewDNSCachingDialer(dialer, cache)
    97  		conn, err := testee.DialContext(ctx, "tcp", addr)
    98  		assert.ErrorIs(t, err, expectedErr)
    99  		assert.Nil(t, conn)
   100  
   101  		cache.AssertExpectations(t)
   102  		dialer.AssertExpectations(t)
   103  	})
   104  
   105  }