// WriteValue writes the given Thrift value to the underlying stream using the // Thrift Binary Protocol. func (bw *Writer) WriteValue(v wire.Value) error { switch v.Type() { case wire.TBool: if v.GetBool() { return bw.writeByte(1) } return bw.writeByte(0) case wire.TI8: return bw.writeByte(byte(v.GetI8())) case wire.TDouble: value := math.Float64bits(v.GetDouble()) return bw.writeInt64(int64(value)) case wire.TI16: return bw.writeInt16(v.GetI16()) case wire.TI32: return bw.writeInt32(v.GetI32()) case wire.TI64: return bw.writeInt64(v.GetI64()) case wire.TBinary: b := v.GetBinary() if err := bw.writeInt32(int32(len(b))); err != nil { return err } return bw.write(b) case wire.TStruct: return bw.writeStruct(v.GetStruct()) case wire.TMap: return bw.writeMap(v.GetMap()) case wire.TSet: return bw.writeSet(v.GetSet()) case wire.TList: return bw.writeList(v.GetList()) default: return fmt.Errorf("unknown ttype %v", v.Type()) } }
// assertRoundTrip checks if x.ToWire() results in the given Value and whether // x.FromWire() with the given value results in the original x. func assertRoundTrip(t *testing.T, x thriftType, v wire.Value, msg string, args ...interface{}) bool { message := fmt.Sprintf(msg, args...) if w, err := x.ToWire(); assert.NoError(t, err, "failed to serialize: %v", x) { if !assert.True( t, wire.ValuesAreEqual(v, w), "%v: %v.ToWire() != %v", message, x, v) { return false } var buff bytes.Buffer if !assert.NoError(t, protocol.Binary.Encode(w, &buff), "%v: failed to serialize", message) { return false } // Flip v to deserialize(serialize(x.ToWire())) to ensure full round // tripping newV, err := protocol.Binary.Decode(bytes.NewReader(buff.Bytes()), v.Type()) if !assert.NoError(t, err, "%v: failed to deserialize", message) { return false } if !assert.True( t, wire.ValuesAreEqual(newV, v), "%v: deserialize(serialize(%v.ToWire())) != %v", message, x, v) { return false } v = newV } xType := reflect.TypeOf(x) if xType.Kind() == reflect.Ptr { xType = xType.Elem() } gotX := reflect.New(xType) err := gotX.MethodByName("FromWire"). Call([]reflect.Value{reflect.ValueOf(v)})[0]. Interface() if assert.Nil(t, err, "FromWire: %v", message) { return assert.Equal(t, x, gotX.Interface(), "FromWire: %v", message) } return false }