1// SPDX-License-Identifier: Apache-2.0
2
3extern crate std;
4
5use std::collections::{BTreeMap, HashMap};
6use std::convert::TryFrom;
7use std::fmt::Debug;
8
9use ciborium::value::Value;
10use ciborium::{cbor, de::from_reader, ser::into_writer};
11
12use rstest::rstest;
13use serde::{de::DeserializeOwned, Deserialize, Serialize};
14
15macro_rules! val {
16 ($x:expr) => {
17 Value::try_from($x).unwrap()
18 };
19}
20
21macro_rules! hex {
22 ($x:expr) => {
23 serde_bytes::ByteBuf::from(hex::decode($x).unwrap())
24 };
25}
26
27macro_rules! map {
28 ($($k:expr => $v:expr),*) => {{
29 let mut map = BTreeMap::new();
30 $(
31 map.insert($k, $v);
32 )*
33 map
34 }}
35}
36
37// Keep the first "case" aligned to a line number ending in 1 for ease in finding tests.
38#[allow(clippy::excessive_precision)]
39#[rstest(input, value, bytes, alternate, equality,
40
41 case(0u8, val!(0u8), "00", false, same),
42 case(0u16, val!(0u16), "00", false, same),
43 case(0u32, val!(0u32), "00", false, same),
44 case(0u64, val!(0u64), "00", false, same),
45 case(0u128, val!(0u128), "00", false, same),
46 case(0i8, val!(0i8), "00", false, same),
47 case(0i16, val!(0i16), "00", false, same),
48 case(0i32, val!(0i32), "00", false, same),
49 case(0i64, val!(0i64), "00", false, same),
50 case(0i128, val!(0i128), "00", false, same),
51 case(1u8, val!(1u8), "01", false, same),
52 case(1u16, val!(1u16), "01", false, same),
53 case(1u32, val!(1u32), "01", false, same),
54 case(1u64, val!(1u64), "01", false, same),
55 case(1u128, val!(1u128), "01", false, same),
56 case(1i8, val!(1i8), "01", false, same),
57 case(1i16, val!(1i16), "01", false, same),
58 case(1i32, val!(1i32), "01", false, same),
59 case(1i64, val!(1i64), "01", false, same),
60 case(1i128, val!(1i128), "01", false, same),
61 case(1u8, val!(1u8), "1b0000000000000001", true, same),
62 case(1u16, val!(1u16), "1b0000000000000001", true, same),
63 case(1u32, val!(1u32), "1b0000000000000001", true, same),
64 case(1u64, val!(1u64), "1b0000000000000001", true, same),
65 case(1u128, val!(1u128), "1b0000000000000001", true, same),
66 case(1i8, val!(1i8), "1b0000000000000001", true, same),
67 case(1i16, val!(1i16), "1b0000000000000001", true, same),
68 case(1i32, val!(1i32), "1b0000000000000001", true, same),
69 case(1i64, val!(1i64), "1b0000000000000001", true, same),
70 case(1i128, val!(1i128), "1b0000000000000001", true, same),
71 case(1u8, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
72 case(1u16, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
73 case(1u32, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
74 case(1u64, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
75 case(1u128, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
76 case(1i8, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
77 case(1i16, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
78 case(1i32, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
79 case(1i64, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
80 case(1i128, bigint(), "c2540000000000000000000000000000000000000001", true, same), // Not In RFC
81 case(10u8, val!(10u8), "0a", false, same),
82 case(10u16, val!(10u16), "0a", false, same),
83 case(10u32, val!(10u32), "0a", false, same),
84 case(10u64, val!(10u64), "0a", false, same),
85 case(10u128, val!(10u128), "0a", false, same),
86 case(10i8, val!(10i8), "0a", false, same),
87 case(10i16, val!(10i16), "0a", false, same),
88 case(10i32, val!(10i32), "0a", false, same),
89 case(10i64, val!(10i64), "0a", false, same),
90 case(10i128, val!(10i128), "0a", false, same),
91 case(23u8, val!(23u8), "17", false, same),
92 case(23u16, val!(23u16), "17", false, same),
93 case(23u32, val!(23u32), "17", false, same),
94 case(23u64, val!(23u64), "17", false, same),
95 case(23u128, val!(23u128), "17", false, same),
96 case(23i8, val!(23i8), "17", false, same),
97 case(23i16, val!(23i16), "17", false, same),
98 case(23i32, val!(23i32), "17", false, same),
99 case(23i64, val!(23i64), "17", false, same),
100 case(23i128, val!(23i128), "17", false, same),
101 case(24u8, val!(24u8), "1818", false, same),
102 case(24u16, val!(24u16), "1818", false, same),
103 case(24u32, val!(24u32), "1818", false, same),
104 case(24u64, val!(24u64), "1818", false, same),
105 case(24u128, val!(24u128), "1818", false, same),
106 case(24i8, val!(24i8), "1818", false, same),
107 case(24i16, val!(24i16), "1818", false, same),
108 case(24i32, val!(24i32), "1818", false, same),
109 case(24i64, val!(24i64), "1818", false, same),
110 case(24i128, val!(24i128), "1818", false, same),
111 case(25u8, val!(25u8), "1819", false, same),
112 case(25u16, val!(25u16), "1819", false, same),
113 case(25u32, val!(25u32), "1819", false, same),
114 case(25u64, val!(25u64), "1819", false, same),
115 case(25u128, val!(25u128), "1819", false, same),
116 case(25i8, val!(25i8), "1819", false, same),
117 case(25i16, val!(25i16), "1819", false, same),
118 case(25i32, val!(25i32), "1819", false, same),
119 case(25i64, val!(25i64), "1819", false, same),
120 case(25i128, val!(25i128), "1819", false, same),
121 case(100u8, val!(100u8), "1864", false, same),
122 case(100u16, val!(100u16), "1864", false, same),
123 case(100u32, val!(100u32), "1864", false, same),
124 case(100u64, val!(100u64), "1864", false, same),
125 case(100u128, val!(100u128), "1864", false, same),
126 case(100i8, val!(100i8), "1864", false, same),
127 case(100i16, val!(100i16), "1864", false, same),
128 case(100i32, val!(100i32), "1864", false, same),
129 case(100i64, val!(100i64), "1864", false, same),
130 case(100i128, val!(100i128), "1864", false, same),
131 case(1000u16, val!(1000u16), "1903e8", false, same),
132 case(1000u32, val!(1000u32), "1903e8", false, same),
133 case(1000u64, val!(1000u64), "1903e8", false, same),
134 case(1000u128, val!(1000u128), "1903e8", false, same),
135 case(1000i16, val!(1000i16), "1903e8", false, same),
136 case(1000i32, val!(1000i32), "1903e8", false, same),
137 case(1000i64, val!(1000i64), "1903e8", false, same),
138 case(1000i128, val!(1000i128), "1903e8", false, same),
139 case(1000000u32, val!(1000000u32), "1a000f4240", false, same),
140 case(1000000u64, val!(1000000u64), "1a000f4240", false, same),
141 case(1000000u128, val!(1000000u128), "1a000f4240", false, same),
142 case(1000000i32, val!(1000000i32), "1a000f4240", false, same),
143 case(1000000i64, val!(1000000i64), "1a000f4240", false, same),
144 case(1000000i128, val!(1000000i128), "1a000f4240", false, same),
145 case(1000000000000u64, val!(1000000000000u64), "1b000000e8d4a51000", false, same),
146 case(1000000000000u128, val!(1000000000000u128), "1b000000e8d4a51000", false, same),
147 case(1000000000000i64, val!(1000000000000i64), "1b000000e8d4a51000", false, same),
148 case(1000000000000i128, val!(1000000000000i128), "1b000000e8d4a51000", false, same),
149 case(18446744073709551615u64, val!(18446744073709551615u64), "1bffffffffffffffff", false, same),
150 case(18446744073709551615u128, val!(18446744073709551615u128), "1bffffffffffffffff", false, same),
151 case(18446744073709551615i128, val!(18446744073709551615i128), "1bffffffffffffffff", false, same),
152 case(18446744073709551616u128, val!(18446744073709551616u128), "c249010000000000000000", false, same),
153 case(18446744073709551616i128, val!(18446744073709551616i128), "c249010000000000000000", false, same),
154 case(-18446744073709551617i128, val!(-18446744073709551617i128), "c349010000000000000000", false, same),
155 case(-18446744073709551616i128, val!(-18446744073709551616i128), "3bffffffffffffffff", false, same),
156 case(-1000i16, val!(-1000i16), "3903e7", false, same),
157 case(-1000i32, val!(-1000i32), "3903e7", false, same),
158 case(-1000i64, val!(-1000i64), "3903e7", false, same),
159 case(-1000i128, val!(-1000i128), "3903e7", false, same),
160 case(-100i8, val!(-100i8), "3863", false, same),
161 case(-100i16, val!(-100i16), "3863", false, same),
162 case(-100i32, val!(-100i32), "3863", false, same),
163 case(-100i64, val!(-100i64), "3863", false, same),
164 case(-100i128, val!(-100i128), "3863", false, same),
165 case(-10i8, val!(-10i8), "29", false, same),
166 case(-10i16, val!(-10i16), "29", false, same),
167 case(-10i32, val!(-10i32), "29", false, same),
168 case(-10i64, val!(-10i64), "29", false, same),
169 case(-10i128, val!(-10i128), "29", false, same),
170 case(-1i8, val!(-1i8), "20", false, same),
171 case(-1i16, val!(-1i16), "20", false, same),
172 case(-1i32, val!(-1i32), "20", false, same),
173 case(-1i64, val!(-1i64), "20", false, same),
174 case(-1i128, val!(-1i128), "20", false, same),
175 case(-1i8, val!(-1i8), "3b0000000000000000", true, same),
176 case(-1i16, val!(-1i16), "3b0000000000000000", true, same),
177 case(-1i32, val!(-1i32), "3b0000000000000000", true, same),
178 case(-1i64, val!(-1i64), "3b0000000000000000", true, same),
179 case(-1i128, val!(-1i128), "3b0000000000000000", true, same),
180 case(0.0f32, val!(0.0f32), "f90000", false, Float),
181 case(0.0f64, val!(0.0f64), "f90000", false, Float),
182 case(-0.0f32, val!(-0.0f32), "f98000", false, Float),
183 case(-0.0f64, val!(-0.0f64), "f98000", false, Float),
184 case(1.0f32, val!(1.0f32), "f93c00", false, Float),
185 case(1.0f64, val!(1.0f64), "f93c00", false, Float),
186 case(1.1f32, val!(1.1f32), "fa3f8ccccd", false, Float), // Not In RFC
187 case(1.1f64, val!(1.1f64), "fb3ff199999999999a", false, Float),
188 case(1.5f32, val!(1.5f32), "f93e00", false, Float),
189 case(1.5f64, val!(1.5f64), "f93e00", false, Float),
190 case(65504.0f32, val!(65504.0f32), "f97bff", false, Float),
191 case(65504.0f64, val!(65504.0f64), "f97bff", false, Float),
192 case(100000.0f32, val!(100000.0f32), "fa47c35000", false, Float),
193 case(100000.0f64, val!(100000.0f64), "fa47c35000", false, Float),
194 case(3.4028234663852886e+38f32, val!(3.4028234663852886e+38f32), "fa7f7fffff", false, Float),
195 case(3.4028234663852886e+38f64, val!(3.4028234663852886e+38f64), "fa7f7fffff", false, Float),
196 case(1.0e+300f64, val!(1.0e+300f64), "fb7e37e43c8800759c", false, Float),
197 case(5.960464477539063e-8f32, val!(5.960464477539063e-8f32), "f90001", false, Float),
198 case(5.960464477539063e-8f64, val!(5.960464477539063e-8f64), "f90001", false, Float),
199 case(0.00006103515625f32, val!(0.00006103515625f32), "f90400", false, Float),
200 case(0.00006103515625f64, val!(0.00006103515625f64), "f90400", false, Float),
201 case(-4.0f32, val!(-4.0f32), "f9c400", false, Float),
202 case(-4.0f64, val!(-4.0f64), "f9c400", false, Float),
203 case(-4.1f32, val!(-4.1f32), "fac0833333", false, Float), // Not In RFC
204 case(-4.1f64, val!(-4.1f64), "fbc010666666666666", false, Float),
205 case(core::f32::INFINITY, val!(core::f32::INFINITY), "f97c00", false, Float),
206 case(core::f64::INFINITY, val!(core::f64::INFINITY), "f97c00", false, Float),
207 case(core::f32::INFINITY, val!(core::f32::INFINITY), "fa7f800000", true, Float),
208 case(core::f64::INFINITY, val!(core::f64::INFINITY), "fa7f800000", true, Float),
209 case(core::f32::INFINITY, val!(core::f32::INFINITY), "fb7ff0000000000000", true, Float),
210 case(core::f64::INFINITY, val!(core::f64::INFINITY), "fb7ff0000000000000", true, Float),
211 case(-core::f32::INFINITY, val!(-core::f32::INFINITY), "f9fc00", false, Float),
212 case(-core::f64::INFINITY, val!(-core::f64::INFINITY), "f9fc00", false, Float),
213 case(-core::f32::INFINITY, val!(-core::f32::INFINITY), "faff800000", true, Float),
214 case(-core::f64::INFINITY, val!(-core::f64::INFINITY), "faff800000", true, Float),
215 case(-core::f32::INFINITY, val!(-core::f32::INFINITY), "fbfff0000000000000", true, Float),
216 case(-core::f64::INFINITY, val!(-core::f64::INFINITY), "fbfff0000000000000", true, Float),
217 case(core::f32::NAN, val!(core::f32::NAN), "f97e00", false, Float),
218 case(core::f64::NAN, val!(core::f64::NAN), "f97e00", false, Float),
219 case(core::f32::NAN, val!(core::f32::NAN), "fa7fc00000", true, Float),
220 case(core::f64::NAN, val!(core::f64::NAN), "fa7fc00000", true, Float),
221 case(core::f32::NAN, val!(core::f32::NAN), "fb7ff8000000000000", true, Float),
222 case(core::f64::NAN, val!(core::f64::NAN), "fb7ff8000000000000", true, Float),
223 case(-core::f32::NAN, val!(-core::f32::NAN), "f9fe00", false, Float), // Not In RFC
224 case(-core::f64::NAN, val!(-core::f64::NAN), "f9fe00", false, Float), // Not In RFC
225 case(-core::f32::NAN, val!(-core::f32::NAN), "faffc00000", true, Float), // Not In RFC
226 case(-core::f64::NAN, val!(-core::f64::NAN), "faffc00000", true, Float), // Not In RFC
227 case(-core::f32::NAN, val!(-core::f32::NAN), "fbfff8000000000000", true, Float), // Not In RFC
228 case(-core::f64::NAN, val!(-core::f64::NAN), "fbfff8000000000000", true, Float), // Not In RFC
229 case(false, val!(false), "f4", false, same),
230 case(true, val!(true), "f5", false, same),
231 case(Value::Null, Value::Null, "f6", false, same),
232 case(hex!(""), val!(&b""[..]), "40", false, same),
233 case(hex!("01020304"), val!(&b"\x01\x02\x03\x04"[..]), "4401020304", false, same),
234 case(hex!("0102030405"), val!(&b"\x01\x02\x03\x04\x05"[..]), "5f42010243030405ff", true, same),
235 case("", val!(""), "60", false, ToOwned::to_owned),
236 case("a", val!("a"), "6161", false, ToOwned::to_owned),
237 case('a', val!('a'), "6161", false, same),
238 case("IETF", val!("IETF"), "6449455446", false, ToOwned::to_owned),
239 case("\"\\", val!("\"\\"), "62225c", false, ToOwned::to_owned),
240 case("ü", val!("ü"), "62c3bc", false, ToOwned::to_owned),
241 case('ü', val!('ü'), "62c3bc", false, same),
242 case("水", val!("水"), "63e6b0b4", false, ToOwned::to_owned),
243 case('水', val!('水'), "63e6b0b4", false, same),
244 case("𐅑", val!("𐅑"), "64f0908591", false, ToOwned::to_owned),
245 case('𐅑', val!('𐅑'), "64f0908591", false, same),
246 case("streaming", val!("streaming"), "7f657374726561646d696e67ff", true, ToOwned::to_owned),
247 case(cbor!([]).unwrap(), Vec::<Value>::new().into(), "80", false, same),
248 case(cbor!([]).unwrap(), Vec::<Value>::new().into(), "9fff", true, same),
249 case(cbor!([1, 2, 3]).unwrap(), cbor!([1, 2, 3]).unwrap(), "83010203", false, same),
250 case(cbor!([1, [2, 3], [4, 5]]).unwrap(), cbor!([1, [2, 3], [4, 5]]).unwrap(), "8301820203820405", false, same),
251 case(cbor!([1, [2, 3], [4, 5]]).unwrap(), cbor!([1, [2, 3], [4, 5]]).unwrap(), "9f018202039f0405ffff", true, same),
252 case(cbor!([1, [2, 3], [4, 5]]).unwrap(), cbor!([1, [2, 3], [4, 5]]).unwrap(), "9f01820203820405ff", true, same),
253 case(cbor!([1, [2, 3], [4, 5]]).unwrap(), cbor!([1, [2, 3], [4, 5]]).unwrap(), "83018202039f0405ff", true, same),
254 case(cbor!([1, [2, 3], [4, 5]]).unwrap(), cbor!([1, [2, 3], [4, 5]]).unwrap(), "83019f0203ff820405", true, same),
255 case((1..=25).collect::<Vec<u8>>(), (1..=25).map(|x| x.into()).collect::<Vec<Value>>().into(), "98190102030405060708090a0b0c0d0e0f101112131415161718181819", false, same),
256 case((1..=25).collect::<Vec<u8>>(), (1..=25).map(|x| x.into()).collect::<Vec<Value>>().into(), "9f0102030405060708090a0b0c0d0e0f101112131415161718181819ff", true, same),
257 case(HashMap::<u8, u8>::new(), Value::Map(vec![]), "a0", false, same),
258 case(BTreeMap::<u8, u8>::new(), Value::Map(vec![]), "a0", false, same),
259 case(map!{1 => 2, 3 => 4}, cbor!({1 => 2, 3 => 4}).unwrap(), "a201020304", false, same),
260 case(cbor!({"a" => 1, "b" => [2, 3]}).unwrap(), cbor!({"a" => 1, "b" => [2, 3]}).unwrap(), "a26161016162820203", false, same),
261 case(cbor!({"a" => 1, "b" => [2, 3]}).unwrap(), cbor!({"a" => 1, "b" => [2, 3]}).unwrap(), "bf61610161629f0203ffff", true, same),
262 case(cbor!(["a", {"b" => "c"}]).unwrap(), cbor!(["a", {"b" => "c"}]).unwrap(), "826161a161626163", false, same),
263 case(cbor!(["a", {"b" => "c"}]).unwrap(), cbor!(["a", {"b" => "c"}]).unwrap(), "826161bf61626163ff", true, same),
264 case(cbor!({"Fun" => true, "Amt" => -2}).unwrap(), cbor!({"Fun" => true, "Amt" => -2}).unwrap(), "bf6346756ef563416d7421ff", true, same),
265 case(map_big(), vmap_big(), "a56161614161626142616361436164614461656145", false, same),
266 case(Option::<u8>::None, Value::Null, "f6", false, same), // Not In RFC
267 case(Option::Some(7u8), val!(7u8), "07", false, same), // Not In RFC
268 case((), Value::Null, "f6", false, same), // Not In RFC
269 case(UnitStruct, Value::Null, "f6", false, same), // Not In RFC
270 case(Newtype(123), val!(123u8), "187b", false, same), // Not In RFC
271 case((22u8, 23u16), cbor!([22, 23]).unwrap(), "821617", false, same), // Not In RFC
272 case(TupleStruct(33, 34), cbor!([33, 34]).unwrap(), "8218211822", false, same), // Not In RFC
273 case(Enum::Unit, cbor!("Unit").unwrap(), "64556e6974", false, same), // Not In RFC
274 case(Enum::Newtype(45), cbor!({"Newtype" => 45}).unwrap(), "a1674e657774797065182d", false, same), // Not In RFC
275 case(Enum::Tuple(56, 67), cbor!({"Tuple" => [56, 67]}).unwrap(), "a1655475706c658218381843", false, same), // Not In RFC
276 case(Enum::Struct { first: 78, second: 89 }, cbor!({ "Struct" => { "first" => 78, "second" => 89 }}).unwrap(), "a166537472756374a2656669727374184e667365636f6e641859", false, same), // Not In RFC
277)]
278fn codec<'de, T: Serialize + Clone, V: Debug + PartialEq + DeserializeOwned, F: Fn(T) -> V>(
279 input: T,
280 value: Value,
281 bytes: &str,
282 alternate: bool,
283 equality: F,
284) {
285 let bytes = hex::decode(bytes).unwrap();
286
287 if !alternate {
288 let mut encoded = Vec::new();
289 into_writer(&input, &mut encoded).unwrap();
290 eprintln!("{:x?} == {:x?}", bytes, encoded);
291 assert_eq!(bytes, encoded);
292
293 let mut encoded = Vec::new();
294 into_writer(&value, &mut encoded).unwrap();
295 eprintln!("{:x?} == {:x?}", bytes, encoded);
296 assert_eq!(bytes, encoded);
297
298 let encoded = Value::serialized(&input).unwrap();
299 eprintln!("{:x?} == {:x?}", &value, &encoded);
300 assert!(veq(&value, &encoded));
301 }
302
303 let decoded: V = from_reader(&bytes[..]).unwrap();
304 let answer = equality(input.clone());
305 eprintln!("{:x?} == {:x?}", answer, decoded);
306 assert_eq!(answer, decoded);
307
308 let decoded: Value = from_reader(&bytes[..]).unwrap();
309 eprintln!("{:x?} == {:x?}", &value, &decoded);
310 assert!(veq(&value, &decoded));
311
312 let decoded: V = value.deserialized().unwrap();
313 let answer = equality(input);
314 eprintln!("{:x?} == {:x?}", answer, decoded);
315 assert_eq!(answer, decoded);
316}
317
318#[inline]
319fn veq(lhs: &Value, rhs: &Value) -> bool {
320 if let Value::Float(l) = lhs {
321 if let Value::Float(r) = rhs {
322 return Float(*l) == Float(*r);
323 }
324 }
325
326 lhs == rhs
327}
328
329#[inline]
330fn same<T>(x: T) -> T {
331 x
332}
333
334#[derive(Debug, Deserialize)]
335struct Float<T>(T);
336
337impl PartialEq for Float<f32> {
338 fn eq(&self, other: &Float<f32>) -> bool {
339 if self.0.is_nan() && other.0.is_nan() {
340 return true;
341 }
342
343 self.0 == other.0
344 }
345}
346
347impl PartialEq for Float<f64> {
348 fn eq(&self, other: &Float<f64>) -> bool {
349 if self.0.is_nan() && other.0.is_nan() {
350 return true;
351 }
352
353 self.0 == other.0
354 }
355}
356
357#[inline]
358fn map_big() -> BTreeMap<String, String> {
359 let mut map = BTreeMap::new();
360 map.insert("a".into(), "A".into());
361 map.insert("b".into(), "B".into());
362 map.insert("c".into(), "C".into());
363 map.insert("d".into(), "D".into());
364 map.insert("e".into(), "E".into());
365 map
366}
367
368#[inline]
369fn vmap_big() -> Value {
370 Value::Map(
371 map_big()
372 .into_iter()
373 .map(|x| (x.0.into(), x.1.into()))
374 .collect(),
375 )
376}
377
378#[inline]
379fn bigint() -> Value {
380 let bytes = hex::decode("0000000000000000000000000000000000000001").unwrap();
381 Value::Tag(2, Value::Bytes(bytes).into())
382}
383
384#[derive(Deserialize, Serialize, Copy, Clone, Debug, PartialEq, Eq)]
385struct UnitStruct;
386
387#[derive(Deserialize, Serialize, Copy, Clone, Debug, PartialEq, Eq)]
388struct TupleStruct(u8, u16);
389
390#[derive(Deserialize, Serialize, Copy, Clone, Debug, PartialEq, Eq)]
391struct Newtype(u8);
392
393#[derive(Deserialize, Serialize, Copy, Clone, Debug, PartialEq, Eq)]
394enum Enum {
395 Unit,
396 Newtype(u8),
397 Tuple(u8, u16),
398 Struct { first: u8, second: u16 },
399}
400
401#[rstest(
402 input,
403 case(vec![]),
404 case(vec![0u8, 1, 2, 3]),
405)]
406fn byte_vec_serde_bytes_compatibility(input: Vec<u8>) {
407 use serde_bytes::ByteBuf;
408
409 let mut buf = Vec::new();
410 into_writer(&input, &mut buf).unwrap();
411 let bytes: ByteBuf = from_reader(&buf[..]).unwrap();
412 assert_eq!(input, bytes.to_vec());
413
414 let mut buf = Vec::new();
415 into_writer(&ByteBuf::from(input.clone()), &mut buf).unwrap();
416 let bytes: Vec<u8> = from_reader(&buf[..]).unwrap();
417 assert_eq!(input, bytes);
418}
419
420#[derive(Serialize, Deserialize, Eq, PartialEq, Debug)]
421struct Foo {
422 bar: u8,
423}
424
425#[rstest(input, expected,
426 case("a163626172182a", Foo { bar: 42 }),
427 case("a143626172182a", Foo { bar: 42 }),
428)]
429fn handle_struct_field_names(input: &str, expected: Foo) {
430 let buf = hex::decode(input).unwrap();
431 let read = from_reader(&buf[..]).unwrap();
432 assert_eq!(expected, read);
433}
434