github.com/hack0072008/kafka-go@v1.0.1/read_test.go (about)

     1  package kafka
     2  
     3  import (
     4  	"bufio"
     5  	"bytes"
     6  	"io/ioutil"
     7  	"math"
     8  	"reflect"
     9  	"testing"
    10  )
    11  
    12  type VarIntTestCase struct {
    13  	v  int64
    14  	r  int
    15  	tc []byte
    16  }
    17  
    18  func TestReadVarInt(t *testing.T) {
    19  	testCases := []*VarIntTestCase{
    20  		{v: 0, r: 3, tc: []byte{0, 1, 10, 0}},
    21  		{v: -1, r: 3, tc: []byte{1, 1, 10, 0}},
    22  		{v: 1, r: 3, tc: []byte{2, 1, 10, 0}},
    23  		{v: -2, r: 3, tc: []byte{3, 1, 10, 0}},
    24  		{v: 2, r: 3, tc: []byte{4, 1, 10, 0}},
    25  		{v: 64, r: 2, tc: []byte{128, 1, 10, 0}},
    26  		{v: -64, r: 3, tc: []byte{127, 1, 10, 0}},
    27  		{v: -196, r: 2, tc: []byte{135, 3, 10, 0}},
    28  		{v: -24772, r: 1, tc: []byte{135, 131, 3, 0}},
    29  	}
    30  
    31  	for _, tc := range testCases {
    32  		var v int64
    33  		rd := bufio.NewReader(bytes.NewReader(tc.tc))
    34  		remain, err := readVarInt(rd, len(tc.tc), &v)
    35  		if err != nil {
    36  			t.Errorf("Failure during reading: %v", err)
    37  		}
    38  		if v != tc.v {
    39  			t.Errorf("Expected %v; got %v", tc.v, v)
    40  		}
    41  		if remain != tc.r {
    42  			t.Errorf("Expected remain %v; got %v", tc.r, remain)
    43  		}
    44  	}
    45  }
    46  
    47  func TestReadVarIntFailing(t *testing.T) {
    48  	var v int64
    49  	testCase := []byte{135, 135}
    50  	rd := bufio.NewReader(bytes.NewReader(testCase))
    51  	_, err := readVarInt(rd, len(testCase), &v)
    52  	if err != errShortRead {
    53  		t.Errorf("Expected error while parsing var int: %v", err)
    54  	}
    55  }
    56  
    57  func TestReadStringArray(t *testing.T) {
    58  	testCases := map[string]struct {
    59  		Value []string
    60  	}{
    61  		"nil": {
    62  			Value: nil,
    63  		},
    64  		"multiple elements": {
    65  			Value: []string{"a", "b", "c"},
    66  		},
    67  	}
    68  
    69  	for label, test := range testCases {
    70  		t.Run(label, func(t *testing.T) {
    71  			b := bytes.NewBuffer(nil)
    72  			w := &writeBuffer{w: b}
    73  			w.writeStringArray(test.Value)
    74  
    75  			var actual []string
    76  			readStringArray(bufio.NewReader(b), b.Len(), &actual)
    77  			if !reflect.DeepEqual(test.Value, actual) {
    78  				t.Errorf("expected %v; got %v", test.Value, actual)
    79  			}
    80  		})
    81  	}
    82  }
    83  
    84  func TestReadMapStringInt32(t *testing.T) {
    85  	testCases := map[string]struct {
    86  		Data map[string][]int32
    87  	}{
    88  		"empty": {
    89  			Data: map[string][]int32{},
    90  		},
    91  		"single element": {
    92  			Data: map[string][]int32{
    93  				"key": {0, 1, 2},
    94  			},
    95  		},
    96  	}
    97  
    98  	for label, test := range testCases {
    99  		t.Run(label, func(t *testing.T) {
   100  			b := bytes.NewBuffer(nil)
   101  			w := &writeBuffer{w: b}
   102  			w.writeInt32(int32(len(test.Data)))
   103  
   104  			for key, values := range test.Data {
   105  				w.writeString(key)
   106  				w.writeInt32Array(values)
   107  			}
   108  
   109  			var actual map[string][]int32
   110  			readMapStringInt32(bufio.NewReader(b), b.Len(), &actual)
   111  			if !reflect.DeepEqual(test.Data, actual) {
   112  				t.Errorf("expected %#v; got %#v", test.Data, actual)
   113  			}
   114  		})
   115  	}
   116  }
   117  
   118  func TestReadNewBytes(t *testing.T) {
   119  
   120  	t.Run("reads new bytes", func(t *testing.T) {
   121  		r := bufio.NewReader(bytes.NewReader([]byte("foobar")))
   122  
   123  		b, remain, err := readNewBytes(r, 6, 3)
   124  		if string(b) != "foo" {
   125  			t.Error("should have returned 3 bytes")
   126  		}
   127  		if remain != 3 {
   128  			t.Error("should have calculated remaining correctly")
   129  		}
   130  		if err != nil {
   131  			t.Error("should not have errored")
   132  		}
   133  
   134  		b, remain, err = readNewBytes(r, remain, 3)
   135  		if string(b) != "bar" {
   136  			t.Error("should have returned 3 bytes")
   137  		}
   138  		if remain != 0 {
   139  			t.Error("should have calculated remaining correctly")
   140  		}
   141  		if err != nil {
   142  			t.Error("should not have errored")
   143  		}
   144  
   145  		b, err = r.Peek(0)
   146  		if len(b) > 0 {
   147  			t.Error("not all bytes were consumed")
   148  		}
   149  	})
   150  
   151  	t.Run("discards bytes when insufficient", func(t *testing.T) {
   152  		r := bufio.NewReader(bytes.NewReader([]byte("foo")))
   153  		b, remain, err := readNewBytes(bufio.NewReader(r), 3, 4)
   154  		if string(b) != "foo" {
   155  			t.Error("should have returned available bytes")
   156  		}
   157  		if remain != 0 {
   158  			t.Error("all bytes should have been consumed")
   159  		}
   160  		if err != errShortRead {
   161  			t.Error("should have returned errShortRead")
   162  		}
   163  		b, err = r.Peek(0)
   164  		if len(b) > 0 {
   165  			t.Error("not all bytes were consumed")
   166  		}
   167  	})
   168  }
   169  
   170  func BenchmarkWriteVarInt(b *testing.B) {
   171  	wb := &writeBuffer{w: ioutil.Discard}
   172  
   173  	for i := 0; i < b.N; i++ {
   174  		wb.writeVarInt(math.MaxInt64)
   175  	}
   176  }
   177  
   178  func BenchmarkReadVarInt(b *testing.B) {
   179  	b1 := new(bytes.Buffer)
   180  	wb := &writeBuffer{w: b1}
   181  
   182  	const N = math.MaxInt64
   183  	wb.writeVarInt(N)
   184  
   185  	b2 := bytes.NewReader(b1.Bytes())
   186  	rb := bufio.NewReader(b2)
   187  	n := b1.Len()
   188  
   189  	for i := 0; i < b.N; i++ {
   190  		v := int64(0)
   191  		r, err := readVarInt(rb, n, &v)
   192  
   193  		if err != nil {
   194  			b.Fatalf("unexpected error reading a varint from the input: %v", err)
   195  		}
   196  
   197  		if r != 0 {
   198  			b.Fatalf("unexpected bytes remaining to be read in the input (%d B)", r)
   199  		}
   200  
   201  		if v != N {
   202  			b.Fatalf("value mismatch, expected %d but found %d", N, v)
   203  		}
   204  
   205  		b2.Reset(b1.Bytes())
   206  		rb.Reset(b2)
   207  	}
   208  }