package frame import ( "encoding/binary" "net" "testing" ) func TestFrameRoundtrip(t *testing.T) { c1, c2 := net.Pipe() defer c1.Close() defer c2.Close() f := NewFrame(FrameVersion, 0x10, 42) if err := f.SetData([]byte("hello frame")); err != nil { t.Fatalf("SetData: %v", err) } go func() { if err := WriteFrame(c1, f); err != nil { t.Errorf("WriteFrame: %v", err) } }() got, err := ReadFrame(c2) if err != nil { t.Fatalf("ReadFrame: %v", err) } if got.Version() != FrameVersion || got.Cmd() != 0x10 || got.StreamID() != 42 { t.Errorf("帧头不符: %s", got.String()) } if string(got.Data()) != "hello frame" { t.Errorf("Data = %q, want hello frame", got.Data()) } } func TestFramePipelineRead(t *testing.T) { // 连续两帧不丢数据(回归:旧实现用临时 bufio.Reader 会吞掉后续帧字节) c1, c2 := net.Pipe() defer c1.Close() defer c2.Close() go func() { a := NewFrame(1, 1, 1) if err := a.SetData([]byte("first")); err != nil { t.Errorf("SetData: %v", err) } b := NewFrame(1, 2, 2) if err := b.SetData([]byte("second")); err != nil { t.Errorf("SetData: %v", err) } if err := WriteFrame(c1, a); err != nil { t.Errorf("WriteFrame: %v", err) } if err := WriteFrame(c1, b); err != nil { t.Errorf("WriteFrame: %v", err) } }() got1, err := ReadFrame(c2) if err != nil || string(got1.Data()) != "first" { t.Fatalf("第一帧 = %q, %v", got1.Data(), err) } got2, err := ReadFrame(c2) if err != nil || string(got2.Data()) != "second" { t.Fatalf("第二帧 = %q, %v", got2.Data(), err) } } func TestSetDataOverflow(t *testing.T) { f := NewFrame(1, 0, 0) if err := f.SetData(make([]byte, 65536)); err == nil { t.Error("超过 65535 字节应返回错误") } if err := f.SetData(make([]byte, 65535)); err != nil { t.Errorf("65535 字节应成功: %v", err) } } func TestMarshalUnmarshal(t *testing.T) { f := NewFrame(1, 3, 9) type payload struct { Name string N int } if err := f.Marshal(payload{Name: "a", N: 1}); err != nil { t.Fatalf("Marshal: %v", err) } var got payload if err := f.Unmarshal(&got); err != nil { t.Fatalf("Unmarshal: %v", err) } if got.Name != "a" || got.N != 1 { t.Errorf("Unmarshal 结果 = %+v", got) } } func TestRawHeader(t *testing.T) { h := RawHeader{} h[0] = 2 h[1] = 7 binary.LittleEndian.PutUint16(h[2:], 300) binary.LittleEndian.PutUint32(h[4:], 100000) if h.Version() != 2 || h.Cmd() != 7 || h.Length() != 300 || h.StreamID() != 100000 { t.Errorf("RawHeader 解析不符: %v %v %v %v", h.Version(), h.Cmd(), h.Length(), h.StreamID()) } if len(h.Bytes()) != 8 { t.Errorf("Bytes 长度 = %d, want 8", len(h.Bytes())) } }