diff options
Diffstat (limited to 'third_party/rust/serde_cbor/tests/enum.rs')
-rw-r--r-- | third_party/rust/serde_cbor/tests/enum.rs | 236 |
1 files changed, 236 insertions, 0 deletions
diff --git a/third_party/rust/serde_cbor/tests/enum.rs b/third_party/rust/serde_cbor/tests/enum.rs new file mode 100644 index 0000000000..630500d6b5 --- /dev/null +++ b/third_party/rust/serde_cbor/tests/enum.rs @@ -0,0 +1,236 @@ +use serde::Serialize; +use serde_cbor; +use serde_cbor::ser::{Serializer, SliceWrite}; + +#[macro_use] +extern crate serde_derive; + +#[test] +fn test_simple_data_enum_roundtrip() { + #[derive(Debug, Serialize, Deserialize, PartialEq)] + enum DataEnum { + A(u32), + B(f32), + } + + let a = DataEnum::A(42); + + let mut slice = [0u8; 64]; + let writer = SliceWrite::new(&mut slice); + let mut serializer = Serializer::new(writer); + a.serialize(&mut serializer).unwrap(); + let writer = serializer.into_inner(); + let end = writer.bytes_written(); + let slice = writer.into_inner(); + let deserialized: DataEnum = + serde_cbor::de::from_slice_with_scratch(&slice[..end], &mut []).unwrap(); + assert_eq!(a, deserialized); +} + +#[cfg(feature = "std")] +mod std_tests { + use std::collections::BTreeMap; + + use serde_cbor::ser::{IoWrite, Serializer}; + use serde_cbor::value::Value; + use serde_cbor::{from_slice, to_vec}; + + pub fn to_vec_legacy<T>(value: &T) -> serde_cbor::Result<Vec<u8>> + where + T: serde::ser::Serialize, + { + let mut vec = Vec::new(); + value.serialize(&mut Serializer::new(&mut IoWrite::new(&mut vec)).legacy_enums())?; + Ok(vec) + } + + #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)] + enum Enum { + A, + B, + } + + #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)] + struct EnumStruct { + e: Enum, + } + + #[test] + fn test_enum() { + let enum_struct = EnumStruct { e: Enum::B }; + let raw = &to_vec(&enum_struct).unwrap(); + println!("raw enum {:?}", raw); + let re: EnumStruct = from_slice(raw).unwrap(); + assert_eq!(enum_struct, re); + } + + #[repr(u16)] + #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)] + enum ReprEnum { + A, + B, + } + + #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)] + struct ReprEnumStruct { + e: ReprEnum, + } + + #[test] + fn test_repr_enum() { + let repr_enum_struct = ReprEnumStruct { e: ReprEnum::B }; + let re: ReprEnumStruct = from_slice(&to_vec(&repr_enum_struct).unwrap()).unwrap(); + assert_eq!(repr_enum_struct, re); + } + + #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)] + enum DataEnum { + A(u32), + B(bool, u8), + C { x: u8, y: String }, + } + + #[test] + fn test_data_enum() { + let data_enum_a = DataEnum::A(4); + let re_a: DataEnum = from_slice(&to_vec(&data_enum_a).unwrap()).unwrap(); + assert_eq!(data_enum_a, re_a); + let data_enum_b = DataEnum::B(true, 42); + let re_b: DataEnum = from_slice(&to_vec(&data_enum_b).unwrap()).unwrap(); + assert_eq!(data_enum_b, re_b); + let data_enum_c = DataEnum::C { + x: 3, + y: "foo".to_owned(), + }; + println!("{:?}", &to_vec(&data_enum_c).unwrap()); + let re_c: DataEnum = from_slice(&to_vec(&data_enum_c).unwrap()).unwrap(); + assert_eq!(data_enum_c, re_c); + } + + #[test] + fn test_serialize() { + assert_eq!(to_vec_legacy(&Enum::A).unwrap(), &[97, 65]); + assert_eq!(to_vec_legacy(&Enum::B).unwrap(), &[97, 66]); + assert_eq!( + to_vec_legacy(&DataEnum::A(42)).unwrap(), + &[130, 97, 65, 24, 42] + ); + assert_eq!( + to_vec_legacy(&DataEnum::B(true, 9)).unwrap(), + &[131, 97, 66, 245, 9] + ); + } + + #[test] + fn test_newtype_struct() { + #[derive(Debug, Deserialize, Serialize, PartialEq, Eq)] + pub struct Newtype(u8); + assert_eq!(to_vec(&142u8).unwrap(), to_vec(&Newtype(142u8)).unwrap()); + assert_eq!(from_slice::<Newtype>(&[24, 142]).unwrap(), Newtype(142)); + } + + #[derive(Deserialize, PartialEq, Debug)] + enum Foo { + #[serde(rename = "require")] + Require, + } + + #[test] + fn test_variable_length_array() { + let slice = b"\x9F\x67\x72\x65\x71\x75\x69\x72\x65\xFF"; + let value: Vec<Foo> = from_slice(slice).unwrap(); + assert_eq!(value, [Foo::Require]); + } + + #[derive(Serialize, Deserialize, PartialEq, Debug)] + enum Bar { + Empty, + Number(i32), + Flag(String, bool), + Point { x: i32, y: i32 }, + } + + #[test] + fn test_enum_as_map() { + // unit variants serialize like bare strings + let empty_s = to_vec_legacy(&Bar::Empty).unwrap(); + let empty_str_s = to_vec_legacy(&"Empty").unwrap(); + assert_eq!(empty_s, empty_str_s); + + // tuple-variants serialize like ["<variant>", values..] + let number_s = to_vec_legacy(&Bar::Number(42)).unwrap(); + let number_vec = vec![Value::Text("Number".to_string()), Value::Integer(42)]; + let number_vec_s = to_vec_legacy(&number_vec).unwrap(); + assert_eq!(number_s, number_vec_s); + + let flag_s = to_vec_legacy(&Bar::Flag("foo".to_string(), true)).unwrap(); + let flag_vec = vec![ + Value::Text("Flag".to_string()), + Value::Text("foo".to_string()), + Value::Bool(true), + ]; + let flag_vec_s = to_vec_legacy(&flag_vec).unwrap(); + assert_eq!(flag_s, flag_vec_s); + + // struct-variants serialize like ["<variant>", {struct..}] + let point_s = to_vec_legacy(&Bar::Point { x: 5, y: -5 }).unwrap(); + let mut struct_map = BTreeMap::new(); + struct_map.insert(Value::Text("x".to_string()), Value::Integer(5)); + struct_map.insert(Value::Text("y".to_string()), Value::Integer(-5)); + let point_vec = vec![ + Value::Text("Point".to_string()), + Value::Map(struct_map.clone()), + ]; + let point_vec_s = to_vec_legacy(&point_vec).unwrap(); + assert_eq!(point_s, point_vec_s); + + // enum_as_map matches serde_json's default serialization for enums. + + // unit variants still serialize like bare strings + let empty_s = to_vec(&Bar::Empty).unwrap(); + assert_eq!(empty_s, empty_str_s); + + // 1-element tuple variants serialize like {"<variant>": value} + let number_s = to_vec(&Bar::Number(42)).unwrap(); + let mut number_map = BTreeMap::new(); + number_map.insert("Number", 42); + let number_map_s = to_vec(&number_map).unwrap(); + assert_eq!(number_s, number_map_s); + + // multi-element tuple variants serialize like {"<variant>": [values..]} + let flag_s = to_vec(&Bar::Flag("foo".to_string(), true)).unwrap(); + let mut flag_map = BTreeMap::new(); + flag_map.insert( + "Flag", + vec![Value::Text("foo".to_string()), Value::Bool(true)], + ); + let flag_map_s = to_vec(&flag_map).unwrap(); + assert_eq!(flag_s, flag_map_s); + + // struct-variants serialize like {"<variant>", {struct..}} + let point_s = to_vec(&Bar::Point { x: 5, y: -5 }).unwrap(); + let mut point_map = BTreeMap::new(); + point_map.insert("Point", Value::Map(struct_map)); + let point_map_s = to_vec(&point_map).unwrap(); + assert_eq!(point_s, point_map_s); + + // deserialization of all encodings should just work + let empty_str_ds = from_slice(&empty_str_s).unwrap(); + assert_eq!(Bar::Empty, empty_str_ds); + + let number_vec_ds = from_slice(&number_vec_s).unwrap(); + assert_eq!(Bar::Number(42), number_vec_ds); + let number_map_ds = from_slice(&number_map_s).unwrap(); + assert_eq!(Bar::Number(42), number_map_ds); + + let flag_vec_ds = from_slice(&flag_vec_s).unwrap(); + assert_eq!(Bar::Flag("foo".to_string(), true), flag_vec_ds); + let flag_map_ds = from_slice(&flag_map_s).unwrap(); + assert_eq!(Bar::Flag("foo".to_string(), true), flag_map_ds); + + let point_vec_ds = from_slice(&point_vec_s).unwrap(); + assert_eq!(Bar::Point { x: 5, y: -5 }, point_vec_ds); + let point_map_ds = from_slice(&point_map_s).unwrap(); + assert_eq!(Bar::Point { x: 5, y: -5 }, point_map_ds); + } +} |