qdrant_client/
serde_deser.rs

1//! Deserialize into any serde type
2//!
3//! Sourced from <https://github.com/serde-rs/json/blob/master/src/value/de.rs>
4
5use std::collections::hash_map::IntoIter;
6
7use serde::de::value::{MapDeserializer, SeqDeserializer};
8use serde::de::{
9    DeserializeSeed, EnumAccess, Expected, IntoDeserializer, Unexpected, VariantAccess, Visitor,
10};
11use serde::Deserializer;
12
13use crate::qdrant::value::Kind;
14use crate::qdrant::{Struct, Value};
15
16#[derive(PartialEq, Eq, Clone)]
17pub enum DeserPayloadError {
18    Error(String),
19    IntegerConversion { got: i64, max: i64 },
20}
21
22impl std::fmt::Debug for DeserPayloadError {
23    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
24        match self {
25            DeserPayloadError::Error(error) => write!(f, "{error}"),
26            DeserPayloadError::IntegerConversion { got, max } => {
27                write!(f, "Overflowing integer conversion: {got} > {max}")
28            }
29        }
30    }
31}
32
33impl std::fmt::Display for DeserPayloadError {
34    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
35        write!(f, "{self:?}")
36    }
37}
38
39impl std::error::Error for DeserPayloadError {}
40
41impl serde::de::Error for DeserPayloadError {
42    fn custom<T>(msg: T) -> Self
43    where
44        T: std::fmt::Display,
45    {
46        Self::Error(msg.to_string())
47    }
48}
49
50impl<'de> IntoDeserializer<'de, DeserPayloadError> for Struct {
51    type Deserializer = MapDeserializer<'de, IntoIter<String, Value>, DeserPayloadError>;
52
53    #[inline]
54    fn into_deserializer(self) -> Self::Deserializer {
55        MapDeserializer::new(self.fields.into_iter())
56    }
57}
58
59impl<'de> IntoDeserializer<'de, DeserPayloadError> for Value {
60    type Deserializer = Self;
61
62    #[inline]
63    fn into_deserializer(self) -> Self::Deserializer {
64        self
65    }
66}
67
68macro_rules! deserialize_number {
69    ($method:ident,$visitorfn:ident,$numsize:ident) => {
70        fn $method<V>(self, visitor: V) -> Result<V::Value, DeserPayloadError>
71        where
72            V: Visitor<'de>,
73        {
74            match self.kind.as_ref() {
75                Some(Kind::IntegerValue(n)) => {
76                    visitor.$visitorfn($numsize::try_from(*n).map_err(|_| {
77                        DeserPayloadError::IntegerConversion {
78                            got: *n,
79                            max: $numsize::MAX as i64,
80                        }
81                    })?)
82                }
83                _ => Err(self.invalid_type(&visitor)),
84            }
85        }
86    };
87}
88
89fn visit_array<'de, V>(array: Vec<Value>, visitor: V) -> Result<V::Value, DeserPayloadError>
90where
91    V: Visitor<'de>,
92{
93    let mut deserializer = SeqDeserializer::new(array.into_iter());
94    let seq = visitor.visit_seq(&mut deserializer)?;
95    deserializer.end()?;
96    Ok(seq)
97}
98
99impl<'de> Deserializer<'de> for Value {
100    type Error = DeserPayloadError;
101
102    fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Self::Error>
103    where
104        V: serde::de::Visitor<'de>,
105    {
106        match self.kind {
107            Some(kind) => match kind {
108                Kind::NullValue(_) => visitor.visit_unit(),
109                Kind::DoubleValue(double) => visitor.visit_f64(double),
110                Kind::IntegerValue(n) => visitor.visit_i64(n),
111                Kind::StringValue(s) => visitor.visit_string(s),
112                Kind::BoolValue(b) => visitor.visit_bool(b),
113                Kind::StructValue(s) => s.into_deserializer().deserialize_any(visitor),
114                Kind::ListValue(list_value) => visit_array(list_value.values, visitor),
115            },
116            None => Err(self.invalid_type(&visitor)),
117        }
118    }
119
120    fn deserialize_bool<V>(self, visitor: V) -> Result<V::Value, Self::Error>
121    where
122        V: serde::de::Visitor<'de>,
123    {
124        match self.kind {
125            Some(Kind::BoolValue(b)) => visitor.visit_bool(b),
126            _ => Err(self.invalid_type(&visitor)),
127        }
128    }
129
130    deserialize_number!(deserialize_i8, visit_i8, i8);
131    deserialize_number!(deserialize_i16, visit_i16, i16);
132    deserialize_number!(deserialize_i32, visit_i32, i32);
133    deserialize_number!(deserialize_i64, visit_i64, i64);
134    deserialize_number!(deserialize_u8, visit_u8, u8);
135    deserialize_number!(deserialize_u16, visit_u16, u16);
136    deserialize_number!(deserialize_u32, visit_u32, u32);
137    deserialize_number!(deserialize_u64, visit_u64, u64);
138
139    fn deserialize_f32<V>(self, visitor: V) -> Result<V::Value, DeserPayloadError>
140    where
141        V: Visitor<'de>,
142    {
143        match self.kind.as_ref() {
144            Some(Kind::DoubleValue(n)) => visitor.visit_f32(*n as f32),
145            _ => Err(self.invalid_type(&visitor)),
146        }
147    }
148
149    fn deserialize_f64<V>(self, visitor: V) -> Result<V::Value, DeserPayloadError>
150    where
151        V: Visitor<'de>,
152    {
153        match self.kind.as_ref() {
154            Some(Kind::DoubleValue(n)) => visitor.visit_f64(*n),
155            _ => Err(self.invalid_type(&visitor)),
156        }
157    }
158
159    fn deserialize_char<V>(self, visitor: V) -> Result<V::Value, Self::Error>
160    where
161        V: serde::de::Visitor<'de>,
162    {
163        self.deserialize_string(visitor)
164    }
165
166    fn deserialize_str<V>(self, visitor: V) -> Result<V::Value, Self::Error>
167    where
168        V: serde::de::Visitor<'de>,
169    {
170        match self.kind {
171            Some(Kind::StringValue(b)) => visitor.visit_str(&b),
172            _ => Err(self.invalid_type(&visitor)),
173        }
174    }
175
176    fn deserialize_string<V>(self, visitor: V) -> Result<V::Value, Self::Error>
177    where
178        V: serde::de::Visitor<'de>,
179    {
180        match self.kind {
181            Some(Kind::StringValue(b)) => visitor.visit_string(b),
182            _ => Err(self.invalid_type(&visitor)),
183        }
184    }
185
186    fn deserialize_bytes<V>(self, visitor: V) -> Result<V::Value, Self::Error>
187    where
188        V: serde::de::Visitor<'de>,
189    {
190        self.deserialize_byte_buf(visitor)
191    }
192
193    fn deserialize_byte_buf<V>(self, visitor: V) -> Result<V::Value, Self::Error>
194    where
195        V: serde::de::Visitor<'de>,
196    {
197        match self.kind {
198            Some(Kind::StringValue(b)) => visitor.visit_string(b),
199            Some(Kind::ListValue(b)) => visit_array(b.values, visitor),
200            _ => Err(self.invalid_type(&visitor)),
201        }
202    }
203
204    fn deserialize_option<V>(self, visitor: V) -> Result<V::Value, Self::Error>
205    where
206        V: serde::de::Visitor<'de>,
207    {
208        if self.kind.is_none() || matches!(self.kind, Some(Kind::NullValue(..))) {
209            return visitor.visit_none();
210        }
211
212        visitor.visit_some(self)
213    }
214
215    fn deserialize_unit<V>(self, visitor: V) -> Result<V::Value, Self::Error>
216    where
217        V: serde::de::Visitor<'de>,
218    {
219        match &self.kind {
220            Some(Kind::NullValue(_)) => visitor.visit_unit(),
221            _ => Err(self.invalid_type(&visitor)),
222        }
223    }
224
225    fn deserialize_unit_struct<V>(
226        self,
227        _name: &'static str,
228        visitor: V,
229    ) -> Result<V::Value, Self::Error>
230    where
231        V: serde::de::Visitor<'de>,
232    {
233        self.deserialize_unit(visitor)
234    }
235
236    fn deserialize_newtype_struct<V>(
237        self,
238        _name: &'static str,
239        visitor: V,
240    ) -> Result<V::Value, Self::Error>
241    where
242        V: serde::de::Visitor<'de>,
243    {
244        visitor.visit_newtype_struct(self)
245    }
246
247    fn deserialize_seq<V>(self, visitor: V) -> Result<V::Value, Self::Error>
248    where
249        V: serde::de::Visitor<'de>,
250    {
251        match self.kind {
252            Some(Kind::ListValue(list)) => visit_array(list.values, visitor),
253            _ => Err(self.invalid_type(&visitor)),
254        }
255    }
256
257    fn deserialize_tuple<V>(self, _len: usize, visitor: V) -> Result<V::Value, Self::Error>
258    where
259        V: serde::de::Visitor<'de>,
260    {
261        self.deserialize_seq(visitor)
262    }
263
264    fn deserialize_tuple_struct<V>(
265        self,
266        _name: &'static str,
267        _len: usize,
268        visitor: V,
269    ) -> Result<V::Value, Self::Error>
270    where
271        V: serde::de::Visitor<'de>,
272    {
273        self.deserialize_seq(visitor)
274    }
275
276    fn deserialize_map<V>(self, visitor: V) -> Result<V::Value, Self::Error>
277    where
278        V: serde::de::Visitor<'de>,
279    {
280        match self.kind {
281            Some(Kind::StructValue(r#struct)) => {
282                r#struct.into_deserializer().deserialize_any(visitor)
283            }
284            _ => Err(self.invalid_type(&visitor)),
285        }
286    }
287
288    fn deserialize_struct<V>(
289        self,
290        _name: &'static str,
291        _fields: &'static [&'static str],
292        visitor: V,
293    ) -> Result<V::Value, Self::Error>
294    where
295        V: serde::de::Visitor<'de>,
296    {
297        match self.kind {
298            Some(k) => match k {
299                Kind::StructValue(r#struct) => {
300                    r#struct.into_deserializer().deserialize_any(visitor)
301                }
302                Kind::ListValue(list) => visit_array(list.values, visitor),
303                _ => Err(Self::invalid_type_from_kind(&k, &visitor)),
304            },
305            None => Err(self.invalid_type(&visitor)),
306        }
307    }
308
309    fn deserialize_enum<V>(
310        self,
311        name: &'static str,
312        variants: &'static [&'static str],
313        visitor: V,
314    ) -> Result<V::Value, Self::Error>
315    where
316        V: serde::de::Visitor<'de>,
317    {
318        match self.kind {
319            Some(k) => match k {
320                Kind::StructValue(r#struct) => r#struct
321                    .into_deserializer()
322                    .deserialize_enum(name, variants, visitor),
323                Kind::StringValue(variant) => visitor.visit_enum(EnumDeserializer { variant }),
324                _ => Err(Self::invalid_type_from_kind(&k, &visitor)),
325            },
326            None => Err(self.invalid_type(&visitor)),
327        }
328    }
329
330    fn deserialize_identifier<V>(self, visitor: V) -> Result<V::Value, Self::Error>
331    where
332        V: serde::de::Visitor<'de>,
333    {
334        self.deserialize_str(visitor)
335    }
336
337    fn deserialize_ignored_any<V>(self, visitor: V) -> Result<V::Value, Self::Error>
338    where
339        V: serde::de::Visitor<'de>,
340    {
341        drop(self);
342        visitor.visit_unit()
343    }
344
345    fn deserialize_i128<V>(self, visitor: V) -> Result<V::Value, Self::Error>
346    where
347        V: Visitor<'de>,
348    {
349        let _ = visitor;
350        Err(serde::de::Error::custom("i128 is not supported"))
351    }
352
353    fn deserialize_u128<V>(self, visitor: V) -> Result<V::Value, Self::Error>
354    where
355        V: Visitor<'de>,
356    {
357        let _ = visitor;
358        Err(serde::de::Error::custom("u128 is not supported"))
359    }
360}
361
362struct EnumDeserializer {
363    variant: String,
364}
365
366impl<'de> EnumAccess<'de> for EnumDeserializer {
367    type Error = DeserPayloadError;
368    type Variant = VariantDeserializer;
369
370    fn variant_seed<V>(self, seed: V) -> Result<(V::Value, VariantDeserializer), Self::Error>
371    where
372        V: DeserializeSeed<'de>,
373    {
374        let variant = self.variant.into_deserializer();
375        let visitor = VariantDeserializer;
376        seed.deserialize(variant).map(|v| (v, visitor))
377    }
378}
379
380struct VariantDeserializer;
381
382impl<'de> VariantAccess<'de> for VariantDeserializer {
383    type Error = DeserPayloadError;
384
385    fn unit_variant(self) -> Result<(), Self::Error> {
386        Ok(())
387    }
388
389    fn newtype_variant_seed<T>(self, _seed: T) -> Result<T::Value, Self::Error>
390    where
391        T: DeserializeSeed<'de>,
392    {
393        Err(serde::de::Error::invalid_type(
394            Unexpected::UnitVariant,
395            &"newtype variant",
396        ))
397    }
398
399    fn tuple_variant<V>(self, _len: usize, _visitor: V) -> Result<V::Value, Self::Error>
400    where
401        V: Visitor<'de>,
402    {
403        Err(serde::de::Error::invalid_type(
404            Unexpected::UnitVariant,
405            &"tuple variant",
406        ))
407    }
408
409    fn struct_variant<V>(
410        self,
411        _fields: &'static [&'static str],
412        _visitor: V,
413    ) -> Result<V::Value, Self::Error>
414    where
415        V: Visitor<'de>,
416    {
417        Err(serde::de::Error::invalid_type(
418            Unexpected::UnitVariant,
419            &"struct variant",
420        ))
421    }
422}
423
424impl Value {
425    #[cold]
426    fn invalid_type<E>(&self, exp: &dyn Expected) -> E
427    where
428        E: serde::de::Error,
429    {
430        serde::de::Error::invalid_type(self.unexpected(), exp)
431    }
432
433    #[cold]
434    fn unexpected<'a>(&'a self) -> Unexpected<'a> {
435        match self.kind.as_ref() {
436            Some(k) => match k {
437                Kind::NullValue(_) => Unexpected::Unit,
438                Kind::DoubleValue(d) => Unexpected::Float(*d),
439                Kind::IntegerValue(i) => Unexpected::Signed(*i),
440                Kind::StringValue(s) => Unexpected::Str(s),
441                Kind::BoolValue(b) => Unexpected::Bool(*b),
442                Kind::StructValue(_) => Unexpected::Map,
443                Kind::ListValue(_) => Unexpected::Seq,
444            },
445            None => Unexpected::Unit,
446        }
447    }
448
449    #[cold]
450    fn invalid_type_from_kind<E>(kind: &Kind, exp: &dyn Expected) -> E
451    where
452        E: serde::de::Error,
453    {
454        serde::de::Error::invalid_type(Self::unexpected_kind(kind), exp)
455    }
456
457    #[cold]
458    fn unexpected_kind<'a>(kind: &'a Kind) -> Unexpected<'a> {
459        match kind {
460            Kind::NullValue(_) => Unexpected::Unit,
461            Kind::DoubleValue(d) => Unexpected::Float(*d),
462            Kind::IntegerValue(i) => Unexpected::Signed(*i),
463            Kind::StringValue(s) => Unexpected::Str(s),
464            Kind::BoolValue(b) => Unexpected::Bool(*b),
465            Kind::StructValue(_) => Unexpected::Map,
466            Kind::ListValue(_) => Unexpected::Seq,
467        }
468    }
469}
470
471#[cfg(test)]
472mod test {
473    use std::collections::{BTreeMap, HashMap};
474
475    use serde::{Deserialize, Serialize};
476    use serde_json::json;
477
478    use crate::serde_deser::DeserPayloadError;
479    use crate::Payload;
480
481    #[test]
482    fn test_json_deser() {
483        #[derive(Deserialize, Serialize, Eq, PartialEq, Debug)]
484        struct S {
485            some_string: String,
486            some_bool: bool,
487            some_int: i32,
488            some_seq: Vec<String>,
489            some_obj: HashMap<String, String>,
490            tuple: (String, u32),
491            #[allow(clippy::type_complexity)]
492            tuple_map: BTreeMap<String, (String, u32, Vec<(u32, String)>)>,
493        }
494
495        let value = S {
496            some_string: "Bar".into(),
497            some_bool: true,
498            some_int: 12,
499            some_seq: vec!["elem1".into(), "elem2".into()],
500            some_obj: HashMap::from([("key".into(), "value".into())]),
501            tuple: ("abc".to_string(), 42),
502            tuple_map: BTreeMap::from([
503                (
504                    "key1".to_string(),
505                    ("42".to_string(), 13, vec![(43, "abc".to_string())]),
506                ),
507                (
508                    "key2".to_string(),
509                    ("rust".to_string(), 91, vec![(84, "python".to_string())]),
510                ),
511            ]),
512        };
513
514        let json_value = serde_json::to_value(&value).unwrap();
515        let payload: Payload = json_value.try_into().unwrap();
516        let deserialized_value: S = payload.deserialize().unwrap();
517
518        assert_eq!(value, deserialized_value)
519    }
520
521    fn make_payload(val: serde_json::Value) -> Payload {
522        val.try_into().expect(
523            "Can only make a json object to Payload. This is a bug in the unit test itself.",
524        )
525    }
526
527    #[test]
528    fn test_integer_conversion() {
529        let payload = make_payload(json!({"integer": u32::MAX}));
530
531        #[derive(Deserialize, Clone)]
532        #[allow(dead_code)]
533        struct DstU8 {
534            integer: u8,
535        }
536
537        // Check fail
538        let got: Result<DstU8, _> = payload.clone().deserialize();
539        assert_eq!(
540            got.err().unwrap().as_payload_deserialization().unwrap(),
541            &DeserPayloadError::IntegerConversion {
542                got: u32::MAX as i64,
543                max: u8::MAX as i64
544            }
545        );
546
547        #[derive(Deserialize, Debug, PartialEq)]
548        #[allow(dead_code)]
549        struct DstU32 {
550            integer: u32,
551        }
552
553        // Check success
554        let got: Result<DstU32, _> = payload.deserialize();
555        assert_eq!(got.unwrap(), DstU32 { integer: u32::MAX });
556    }
557
558    #[test]
559    fn test_nested() {
560        let payload = make_payload(json!({"number": 42, "data": {"text": "abc", "num": 99}}));
561
562        #[derive(Deserialize)]
563        #[allow(dead_code)]
564        struct Dst {
565            number: u32,
566            data: DstData,
567        }
568
569        #[derive(Deserialize)]
570        #[allow(dead_code)]
571        struct DstData {
572            text: String,
573            num: u8,
574        }
575
576        let dst: Dst = payload.deserialize().unwrap();
577        assert_eq!(dst.number, 42);
578        assert_eq!(dst.data.num, 99);
579        assert_eq!(dst.data.text, "abc");
580    }
581
582    #[test]
583    fn test_tuple() {
584        let payload = make_payload(json!({"number": 42, "seq": [1,2,3]}));
585
586        #[derive(Deserialize)]
587        #[allow(dead_code)]
588        struct Dst {
589            number: u32,
590            seq: (u8, u8, u8),
591        }
592
593        let dst: Dst = payload.clone().deserialize().unwrap();
594        assert_eq!(dst.seq, (1, 2, 3));
595
596        #[derive(Deserialize)]
597        #[allow(dead_code)]
598        struct DstTooShort {
599            number: u32,
600            seq: (u8, u8),
601        }
602
603        let dst: Result<DstTooShort, _> = payload.clone().deserialize();
604        assert!(dst.is_err());
605
606        #[derive(Deserialize)]
607        #[allow(dead_code)]
608        struct DstTooLong {
609            number: u32,
610            seq: (u8, u8, u8, u8),
611        }
612
613        let dst: Result<DstTooLong, _> = payload.deserialize();
614        assert!(dst.is_err());
615    }
616
617    #[test]
618    fn test_enum() {
619        let payload = make_payload(json!({"items": ["Major","Minor","Mid"]}));
620
621        #[derive(Deserialize, Debug)]
622        #[allow(dead_code)]
623        struct Dst {
624            items: Vec<DstEnum>,
625        }
626
627        #[derive(Deserialize, PartialEq, Debug)]
628        #[allow(dead_code)]
629        enum DstEnum {
630            Major,
631            Minor,
632            Mid,
633            SomewhereElse,
634        }
635
636        let dst: Dst = payload.deserialize().unwrap();
637        assert_eq!(
638            dst.items,
639            vec![DstEnum::Major, DstEnum::Minor, DstEnum::Mid]
640        );
641
642        let payload = make_payload(json!({"items": ["Major","Minor","Middle"]})); // "Middle" is no enum variant.
643        let dst: Result<Dst, _> = payload.deserialize();
644        assert!(dst.is_err())
645    }
646
647    #[test]
648    fn test_enum_tuple_struct() {
649        let payload = make_payload(json!({"items": ["Major",32,true]}));
650
651        #[derive(Deserialize, Debug)]
652        #[allow(dead_code)]
653        struct Dst {
654            items: Vec<DstEnum>,
655        }
656
657        #[derive(Deserialize, PartialEq, Debug)]
658        #[allow(dead_code)]
659        #[serde(untagged)]
660        enum DstEnum {
661            Str(String),
662            Num(i32),
663            Bool(bool),
664        }
665
666        let dst: Dst = payload.deserialize().unwrap();
667        assert_eq!(
668            dst.items,
669            vec![
670                DstEnum::Str("Major".to_string()),
671                DstEnum::Num(32),
672                DstEnum::Bool(true)
673            ]
674        );
675    }
676
677    #[test]
678    fn test_enum_struct() {
679        let payload = make_payload(json!({"items": [{"key": "Major"},{"other": 32},true]}));
680
681        #[derive(Deserialize, Debug)]
682        #[allow(dead_code)]
683        struct Dst {
684            items: Vec<DstEnum>,
685        }
686
687        #[derive(Deserialize, PartialEq, Debug)]
688        #[allow(dead_code)]
689        #[serde(untagged)]
690        enum DstEnum {
691            First { key: String },
692            Second { other: u32 },
693            Bool(bool),
694        }
695
696        let dst: Dst = payload.deserialize().unwrap();
697        assert_eq!(
698            dst.items,
699            vec![
700                DstEnum::First {
701                    key: "Major".to_string()
702                },
703                DstEnum::Second { other: 32 },
704                DstEnum::Bool(true)
705            ]
706        );
707
708        let payload_direct =
709            make_payload(json!({"item": {"key": "Major"}, "other": {"other": 32}, "third": false}));
710
711        #[derive(Deserialize, Debug)]
712        #[allow(dead_code)]
713        struct Dst2 {
714            item: DstEnum,
715            other: DstEnum,
716            third: DstEnum,
717        }
718
719        let dst: Dst2 = payload_direct.deserialize().unwrap();
720        assert_eq!(
721            dst.item,
722            DstEnum::First {
723                key: "Major".to_string()
724            }
725        );
726        assert_eq!(dst.other, DstEnum::Second { other: 32 });
727        assert_eq!(dst.third, DstEnum::Bool(false));
728
729        let dst_err: Result<Dst2, _> = make_payload(
730            json!({"item": {"key2": "Major"}, "other": {"other": 32}, "third": false}),
731        )
732        .deserialize();
733        assert!(dst_err.is_err())
734    }
735
736    #[test]
737    fn test_enum_struct_tagged() {
738        let payload = make_payload(
739            json!({"items": [{"t": "First", "c": {"key": "Major"}}, {"t": "Second","c": {"other": 32}},{"t": "Bool", "c": true}]}),
740        );
741
742        #[derive(Deserialize, Debug)]
743        #[allow(dead_code)]
744        struct Dst {
745            items: Vec<DstEnum>,
746        }
747
748        #[derive(Deserialize, PartialEq, Debug)]
749        #[allow(dead_code)]
750        #[serde(tag = "t", content = "c")]
751        enum DstEnum {
752            First { key: String },
753            Second { other: u32 },
754            Bool(bool),
755        }
756
757        let dst: Dst = payload.deserialize().unwrap();
758        assert_eq!(
759            dst.items,
760            vec![
761                DstEnum::First {
762                    key: "Major".to_string()
763                },
764                DstEnum::Second { other: 32 },
765                DstEnum::Bool(true)
766            ]
767        );
768    }
769
770    #[test]
771    fn test_option() {
772        let payload = make_payload(json!({
773            "str1": "hi",
774            "int1": 32,
775            "vec1": [42]
776        }));
777
778        #[derive(Deserialize, Debug, PartialEq)]
779        #[allow(dead_code)]
780        struct Dst {
781            str1: Option<String>,
782            str2: Option<String>,
783            int1: Option<i32>,
784            #[serde(skip_serializing_if = "Option::is_none")]
785            int2: Option<i32>,
786            vec1: Option<Vec<u32>>,
787            vec2: Option<Vec<u32>>,
788        }
789
790        let dst: Dst = payload.deserialize().unwrap();
791        assert_eq!(
792            dst,
793            Dst {
794                str1: Some("hi".to_string()),
795                str2: None,
796                int1: Some(32),
797                int2: None,
798                vec1: Some(vec![42]),
799                vec2: None,
800            }
801        )
802    }
803
804    #[test]
805    fn test_other_types() {
806        let payload = make_payload(json!({
807            "bytes": [0,4,15,11,96,12],
808            "double": 0.2,
809            "null": None::<u32>,
810            "single_char": 'c',
811        }));
812
813        #[derive(Deserialize, Debug, PartialEq)]
814        #[allow(dead_code)]
815        struct Dst {
816            bytes: Vec<u8>,
817            double: f32,
818            null: (),
819            single_char: char,
820        }
821
822        let dst: Dst = payload.deserialize().unwrap();
823        assert_eq!(dst.bytes, vec![0, 4, 15, 11, 96, 12]);
824        assert_eq!(dst.double, 0.2);
825        assert_eq!(dst.single_char, 'c');
826    }
827}