package git import ( "bytes" "io" "testing" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" ) type PacketReadTestCase struct { In []byte Payload []byte Err string } func (c *PacketReadTestCase) Assert(t *testing.T) { buf := bytes.NewReader(c.In) rw := newPktline(buf, nil) pkt, err := rw.readPacket() if len(c.Payload) > 0 { assert.Equal(t, c.Payload, pkt) } else { assert.Empty(t, pkt) } if len(c.Err) > 0 { require.NotNil(t, err) assert.Equal(t, c.Err, err.Error()) } else { assert.Nil(t, err) } } func TestPktLineReadsWholePackets(t *testing.T) { tc := &PacketReadTestCase{ In: []byte{ 0x30, 0x30, 0x30, 0x38, // 0008 (hex. length) 0x1, 0x2, 0x3, 0x4, // payload }, Payload: []byte{0x1, 0x2, 0x3, 0x4}, } tc.Assert(t) } func TestPktLineNoPacket(t *testing.T) { tc := &PacketReadTestCase{ In: []byte{}, Err: io.EOF.Error(), } tc.Assert(t) } func TestPktLineEmptyPacket(t *testing.T) { tc := &PacketReadTestCase{ In: []byte{ 0x30, 0x30, 0x30, 0x34, // No body (invalid) }, Err: "Invalid packet length.", } tc.Assert(t) } func TestPktLineFlushPacket(t *testing.T) { tc := &PacketReadTestCase{ In: []byte{0x30, 0x30, 0x30, 0x30}, // Flush packet Payload: []byte{}, Err: "", } tc.Assert(t) } func TestPktLineDiscardsPacketsWithUnparseableLength(t *testing.T) { tc := &PacketReadTestCase{ In: []byte{ 0xff, 0xff, 0xff, 0xff, // ÿÿÿÿ (invalid hex. length) // No body }, Err: "strconv.ParseInt: parsing \"\\xff\\xff\\xff\\xff\": invalid syntax", } tc.Assert(t) } func TestPktLineReadsTextWithNewline(t *testing.T) { rw := newPktline(bytes.NewReader([]byte{ 0x30, 0x30, 0x30, 0x39, // 0009 (hex. length) 0x61, 0x62, 0x63, 0x64, 0xa, // Empty body }), nil) str, err := rw.readPacketText() assert.Nil(t, err) assert.Equal(t, "abcd", str) } func TestPktLineReadsTextWithoutNewline(t *testing.T) { rw := newPktline(bytes.NewReader([]byte{ 0x30, 0x30, 0x30, 0x38, // 0009 (hex. length) 0x61, 0x62, 0x63, 0x64, }), nil) str, err := rw.readPacketText() assert.Nil(t, err) assert.Equal(t, "abcd", str) } func TestPktLineReadsTextWithErr(t *testing.T) { rw := newPktline(bytes.NewReader([]byte{ 0x30, 0x30, 0x30, 0x34, // 0004 (hex. length) // No body }), nil) str, err := rw.readPacketText() require.NotNil(t, err) assert.Equal(t, "Invalid packet length.", err.Error()) assert.Equal(t, "", str) } func TestPktLineAppendsPacketLists(t *testing.T) { rw := newPktline(bytes.NewReader([]byte{ 0x30, 0x30, 0x30, 0x38, // 0009 (hex. length) 0x61, 0x62, 0x63, 0x64, // "abcd" 0x30, 0x30, 0x30, 0x38, // 0008 (hex. length) 0x65, 0x66, 0x67, 0x68, // "efgh" 0x30, 0x30, 0x30, 0x30, // 0000 (hex. length) }), nil) str, err := rw.readPacketList() assert.Nil(t, err) assert.Equal(t, []string{"abcd", "efgh"}, str) } func TestPktLineAppendsPacketListsAndReturnsErrs(t *testing.T) { rw := newPktline(bytes.NewReader([]byte{ 0x30, 0x30, 0x30, 0x38, // 0009 (hex. length) 0x61, 0x62, 0x63, 0x64, // "abcd" 0x30, 0x30, 0x30, 0x34, // 0004 (hex. length) // No body }), nil) str, err := rw.readPacketList() require.NotNil(t, err) assert.Equal(t, "Invalid packet length.", err.Error()) assert.Empty(t, str) } func TestPktLineWritesPackets(t *testing.T) { var buf bytes.Buffer rw := newPktline(nil, &buf) require.Nil(t, rw.writePacket([]byte{ 0x1, 0x2, 0x3, 0x4, })) require.Nil(t, rw.writeFlush()) assert.Equal(t, []byte{ 0x30, 0x30, 0x30, 0x38, // 0008 (hex. length) 0x1, 0x2, 0x3, 0x4, // payload 0x30, 0x30, 0x30, 0x30, // 0000 (flush packet) }, buf.Bytes()) } func TestPktLineWritesPacketsEqualToMaxLength(t *testing.T) { var buf bytes.Buffer rw := newPktline(nil, &buf) err := rw.writePacket(make([]byte, MaxPacketLength)) assert.Nil(t, err) assert.Equal(t, 4+MaxPacketLength, len(buf.Bytes())) } func TestPktLineDoesNotWritePacketsExceedingMaxLength(t *testing.T) { var buf bytes.Buffer rw := newPktline(nil, &buf) err := rw.writePacket(make([]byte, MaxPacketLength+1)) require.NotNil(t, err) assert.Equal(t, "Packet length exceeds maximal length", err.Error()) assert.Empty(t, buf.Bytes()) } func TestPktLineWritesPacketText(t *testing.T) { var buf bytes.Buffer rw := newPktline(nil, &buf) require.Nil(t, rw.writePacketText("abcd")) require.Nil(t, rw.writeFlush()) assert.Equal(t, []byte{ 0x30, 0x30, 0x30, 0x39, // 0009 (hex. length) 0x61, 0x62, 0x63, 0x64, 0xa, // "abcd\n" (payload) 0x30, 0x30, 0x30, 0x30, // 0000 (flush packet) }, buf.Bytes()) } func TestPktLineWritesPacketLists(t *testing.T) { var buf bytes.Buffer rw := newPktline(nil, &buf) err := rw.writePacketList([]string{"foo", "bar"}) assert.Nil(t, err) assert.Equal(t, []byte{ 0x30, 0x30, 0x30, 0x38, // 0008 (hex. length) 0x66, 0x6f, 0x6f, 0xa, // "foo\n" (payload) 0x30, 0x30, 0x30, 0x38, // 0008 (hex. length) 0x62, 0x61, 0x72, 0xa, // "bar\n" (payload) 0x30, 0x30, 0x30, 0x30, // 0000 (hex. length) }, buf.Bytes()) }