1 use serde::Serialize;
2 use serde_cbor;
3 use serde_cbor::ser::{Serializer, SliceWrite};
4 
5 #[macro_use]
6 extern crate serde_derive;
7 
8 #[test]
test_simple_data_enum_roundtrip()9 fn test_simple_data_enum_roundtrip() {
10     #[derive(Debug, Serialize, Deserialize, PartialEq)]
11     enum DataEnum {
12         A(u32),
13         B(f32),
14     }
15 
16     let a = DataEnum::A(42);
17 
18     let mut slice = [0u8; 64];
19     let writer = SliceWrite::new(&mut slice);
20     let mut serializer = Serializer::new(writer);
21     a.serialize(&mut serializer).unwrap();
22     let writer = serializer.into_inner();
23     let end = writer.bytes_written();
24     let slice = writer.into_inner();
25     let deserialized: DataEnum =
26         serde_cbor::de::from_slice_with_scratch(&slice[..end], &mut []).unwrap();
27     assert_eq!(a, deserialized);
28 }
29 
30 #[cfg(feature = "std")]
31 mod std_tests {
32     use std::collections::BTreeMap;
33 
34     use serde_cbor::ser::{IoWrite, Serializer};
35     use serde_cbor::value::Value;
36     use serde_cbor::{from_slice, to_vec};
37 
to_vec_legacy<T>(value: &T) -> serde_cbor::Result<Vec<u8>> where T: serde::ser::Serialize,38     pub fn to_vec_legacy<T>(value: &T) -> serde_cbor::Result<Vec<u8>>
39     where
40         T: serde::ser::Serialize,
41     {
42         let mut vec = Vec::new();
43         value.serialize(&mut Serializer::new(&mut IoWrite::new(&mut vec)).legacy_enums())?;
44         Ok(vec)
45     }
46 
47     #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)]
48     enum Enum {
49         A,
50         B,
51     }
52 
53     #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)]
54     struct EnumStruct {
55         e: Enum,
56     }
57 
58     #[test]
test_enum()59     fn test_enum() {
60         let enum_struct = EnumStruct { e: Enum::B };
61         let raw = &to_vec(&enum_struct).unwrap();
62         println!("raw enum {:?}", raw);
63         let re: EnumStruct = from_slice(raw).unwrap();
64         assert_eq!(enum_struct, re);
65     }
66 
67     #[repr(u16)]
68     #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)]
69     enum ReprEnum {
70         A,
71         B,
72     }
73 
74     #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)]
75     struct ReprEnumStruct {
76         e: ReprEnum,
77     }
78 
79     #[test]
test_repr_enum()80     fn test_repr_enum() {
81         let repr_enum_struct = ReprEnumStruct { e: ReprEnum::B };
82         let re: ReprEnumStruct = from_slice(&to_vec(&repr_enum_struct).unwrap()).unwrap();
83         assert_eq!(repr_enum_struct, re);
84     }
85 
86     #[derive(Debug, Serialize, Deserialize, PartialEq, Eq)]
87     enum DataEnum {
88         A(u32),
89         B(bool, u8),
90         C { x: u8, y: String },
91     }
92 
93     #[test]
test_data_enum()94     fn test_data_enum() {
95         let data_enum_a = DataEnum::A(4);
96         let re_a: DataEnum = from_slice(&to_vec(&data_enum_a).unwrap()).unwrap();
97         assert_eq!(data_enum_a, re_a);
98         let data_enum_b = DataEnum::B(true, 42);
99         let re_b: DataEnum = from_slice(&to_vec(&data_enum_b).unwrap()).unwrap();
100         assert_eq!(data_enum_b, re_b);
101         let data_enum_c = DataEnum::C {
102             x: 3,
103             y: "foo".to_owned(),
104         };
105         println!("{:?}", &to_vec(&data_enum_c).unwrap());
106         let re_c: DataEnum = from_slice(&to_vec(&data_enum_c).unwrap()).unwrap();
107         assert_eq!(data_enum_c, re_c);
108     }
109 
110     #[test]
test_serialize()111     fn test_serialize() {
112         assert_eq!(to_vec_legacy(&Enum::A).unwrap(), &[97, 65]);
113         assert_eq!(to_vec_legacy(&Enum::B).unwrap(), &[97, 66]);
114         assert_eq!(
115             to_vec_legacy(&DataEnum::A(42)).unwrap(),
116             &[130, 97, 65, 24, 42]
117         );
118         assert_eq!(
119             to_vec_legacy(&DataEnum::B(true, 9)).unwrap(),
120             &[131, 97, 66, 245, 9]
121         );
122     }
123 
124     #[test]
test_newtype_struct()125     fn test_newtype_struct() {
126         #[derive(Debug, Deserialize, Serialize, PartialEq, Eq)]
127         pub struct Newtype(u8);
128         assert_eq!(to_vec(&142u8).unwrap(), to_vec(&Newtype(142u8)).unwrap());
129         assert_eq!(from_slice::<Newtype>(&[24, 142]).unwrap(), Newtype(142));
130     }
131 
132     #[derive(Deserialize, PartialEq, Debug)]
133     enum Foo {
134         #[serde(rename = "require")]
135         Require,
136     }
137 
138     #[test]
test_variable_length_array()139     fn test_variable_length_array() {
140         let slice = b"\x9F\x67\x72\x65\x71\x75\x69\x72\x65\xFF";
141         let value: Vec<Foo> = from_slice(slice).unwrap();
142         assert_eq!(value, [Foo::Require]);
143     }
144 
145     #[derive(Serialize, Deserialize, PartialEq, Debug)]
146     enum Bar {
147         Empty,
148         Number(i32),
149         Flag(String, bool),
150         Point { x: i32, y: i32 },
151     }
152 
153     #[test]
test_enum_as_map()154     fn test_enum_as_map() {
155         // unit variants serialize like bare strings
156         let empty_s = to_vec_legacy(&Bar::Empty).unwrap();
157         let empty_str_s = to_vec_legacy(&"Empty").unwrap();
158         assert_eq!(empty_s, empty_str_s);
159 
160         // tuple-variants serialize like ["<variant>", values..]
161         let number_s = to_vec_legacy(&Bar::Number(42)).unwrap();
162         let number_vec = vec![Value::Text("Number".to_string()), Value::Integer(42)];
163         let number_vec_s = to_vec_legacy(&number_vec).unwrap();
164         assert_eq!(number_s, number_vec_s);
165 
166         let flag_s = to_vec_legacy(&Bar::Flag("foo".to_string(), true)).unwrap();
167         let flag_vec = vec![
168             Value::Text("Flag".to_string()),
169             Value::Text("foo".to_string()),
170             Value::Bool(true),
171         ];
172         let flag_vec_s = to_vec_legacy(&flag_vec).unwrap();
173         assert_eq!(flag_s, flag_vec_s);
174 
175         // struct-variants serialize like ["<variant>", {struct..}]
176         let point_s = to_vec_legacy(&Bar::Point { x: 5, y: -5 }).unwrap();
177         let mut struct_map = BTreeMap::new();
178         struct_map.insert(Value::Text("x".to_string()), Value::Integer(5));
179         struct_map.insert(Value::Text("y".to_string()), Value::Integer(-5));
180         let point_vec = vec![
181             Value::Text("Point".to_string()),
182             Value::Map(struct_map.clone()),
183         ];
184         let point_vec_s = to_vec_legacy(&point_vec).unwrap();
185         assert_eq!(point_s, point_vec_s);
186 
187         // enum_as_map matches serde_json's default serialization for enums.
188 
189         // unit variants still serialize like bare strings
190         let empty_s = to_vec(&Bar::Empty).unwrap();
191         assert_eq!(empty_s, empty_str_s);
192 
193         // 1-element tuple variants serialize like {"<variant>": value}
194         let number_s = to_vec(&Bar::Number(42)).unwrap();
195         let mut number_map = BTreeMap::new();
196         number_map.insert("Number", 42);
197         let number_map_s = to_vec(&number_map).unwrap();
198         assert_eq!(number_s, number_map_s);
199 
200         // multi-element tuple variants serialize like {"<variant>": [values..]}
201         let flag_s = to_vec(&Bar::Flag("foo".to_string(), true)).unwrap();
202         let mut flag_map = BTreeMap::new();
203         flag_map.insert(
204             "Flag",
205             vec![Value::Text("foo".to_string()), Value::Bool(true)],
206         );
207         let flag_map_s = to_vec(&flag_map).unwrap();
208         assert_eq!(flag_s, flag_map_s);
209 
210         // struct-variants serialize like {"<variant>", {struct..}}
211         let point_s = to_vec(&Bar::Point { x: 5, y: -5 }).unwrap();
212         let mut point_map = BTreeMap::new();
213         point_map.insert("Point", Value::Map(struct_map));
214         let point_map_s = to_vec(&point_map).unwrap();
215         assert_eq!(point_s, point_map_s);
216 
217         // deserialization of all encodings should just work
218         let empty_str_ds = from_slice(&empty_str_s).unwrap();
219         assert_eq!(Bar::Empty, empty_str_ds);
220 
221         let number_vec_ds = from_slice(&number_vec_s).unwrap();
222         assert_eq!(Bar::Number(42), number_vec_ds);
223         let number_map_ds = from_slice(&number_map_s).unwrap();
224         assert_eq!(Bar::Number(42), number_map_ds);
225 
226         let flag_vec_ds = from_slice(&flag_vec_s).unwrap();
227         assert_eq!(Bar::Flag("foo".to_string(), true), flag_vec_ds);
228         let flag_map_ds = from_slice(&flag_map_s).unwrap();
229         assert_eq!(Bar::Flag("foo".to_string(), true), flag_map_ds);
230 
231         let point_vec_ds = from_slice(&point_vec_s).unwrap();
232         assert_eq!(Bar::Point { x: 5, y: -5 }, point_vec_ds);
233         let point_map_ds = from_slice(&point_map_s).unwrap();
234         assert_eq!(Bar::Point { x: 5, y: -5 }, point_map_ds);
235     }
236 }
237