Skip to main content

cbor_core/ext/
serde.rs

1//! Serde integration for CBOR [`Value`].
2//!
3//! This module provides [`Serialize`] and [`Deserialize`] implementations
4//! for [`Value`]. Conversion between arbitrary Rust types and [`Value`]
5//! is performed through the inherent methods [`Value::serialized`] and
6//! [`Value::deserialized`]. The module also defines the
7//! [`SerdeError`] type returned by these conversions.
8//!
9//! # Converting Rust types to `Value`
10//!
11//! Any type that implements [`Serialize`] can be converted into a
12//! [`Value`] with [`Value::serialized`]:
13//!
14//! ```
15//! use cbor_core::Value;
16//! use serde::Serialize;
17//!
18//! #[derive(Serialize)]
19//! struct Sensor {
20//!     id: u32,
21//!     label: String,
22//!     readings: Vec<f64>,
23//! }
24//!
25//! let s = Sensor {
26//!     id: 7,
27//!     label: "temperature".into(),
28//!     readings: vec![20.5, 21.0, 19.8],
29//! };
30//!
31//! let v = Value::serialized(&s).unwrap();
32//! assert_eq!(v["id"].to_u32().unwrap(), 7);
33//! assert_eq!(v["label"].as_str().unwrap(), "temperature");
34//! assert_eq!(v["readings"][0].to_f64().unwrap(), 20.5);
35//! ```
36//!
37//! # Converting `Value` to Rust types
38//!
39//! [`Value::deserialized`] goes the other direction, extracting a
40//! [`Deserialize`] type from a [`Value`]:
41//!
42//! ```
43//! use cbor_core::{Value, map, array};
44//! use serde::Deserialize;
45//!
46//! #[derive(Deserialize, Debug, PartialEq)]
47//! struct Sensor {
48//!     id: u32,
49//!     label: String,
50//!     readings: Vec<f64>,
51//! }
52//!
53//! let v = map! {
54//!     "id" => 7,
55//!     "label" => "temperature",
56//!     "readings" => array![20.5, 21.0, 19.8],
57//! };
58//!
59//! let s: Sensor = v.deserialized().unwrap();
60//! assert_eq!(s.id, 7);
61//! assert_eq!(s.label, "temperature");
62//! ```
63//!
64//! # Going directly between bytes and Rust types
65//!
66//! Combining [`Value::serialized`] / [`Value::deserialized`] with
67//! [`Value::encode`], [`Value::decode`], [`Value::encode_hex`], and
68//! [`Value::decode_hex`] gives concise round-trips through the wire
69//! format:
70//!
71//! ```
72//! use cbor_core::Value;
73//! use serde::{Deserialize, Serialize};
74//!
75//! #[derive(Serialize, Deserialize, Debug, PartialEq)]
76//! struct Point { x: i32, y: i32 }
77//!
78//! let p = Point { x: 1, y: 2 };
79//!
80//! let hex = Value::serialized(&p).unwrap().encode_hex();
81//! let back: Point = Value::decode_hex(&hex).unwrap().deserialized().unwrap();
82//! assert_eq!(back, p);
83//! ```
84//!
85//! # Serializing `Value` with other formats
86//!
87//! Because [`Value`] implements [`Serialize`] and [`Deserialize`], it
88//! works directly with any serde-based format such as JSON:
89//!
90//! ```
91//! use cbor_core::{Value, map};
92//!
93//! let v = map! { "x" => 1, "y" => 2 };
94//! let json = serde_json::to_string(&v).unwrap();
95//!
96//! let back: Value = serde_json::from_str(&json).unwrap();
97//! assert_eq!(back["x"].to_i32().unwrap(), 1);
98//! ```
99//!
100//! # Tags and CBOR-specific types
101//!
102//! The serde data model does not have a notion of CBOR tags or simple
103//! values. During deserialization, tags are stripped and their inner
104//! content is used directly, with the exception of big integers
105//! (tags 2 and 3), which are recognized and deserialized as integers.
106//! During serialization, tags are only emitted for big integers that
107//! exceed the `u64`/`i64` range; all other values are untagged.
108//!
109//! Tagged values and arbitrary simple values cannot be created through
110//! the serde interface. For full control over the encoded CBOR
111//! structure, build [`Value`]s directly using the constructors on
112//! [`Value`] (e.g. [`Value::tag`], [`Value::simple_value`]).
113
114use std::collections::BTreeMap;
115use std::fmt;
116
117use serde::de::{self, DeserializeSeed, Deserializer as _, MapAccess, SeqAccess, Visitor};
118use serde::ser::{self, SerializeMap, SerializeSeq};
119use serde::{Deserialize, Serialize};
120
121use crate::Value;
122
123// ---------------------------------------------------------------------------
124// Error
125// ---------------------------------------------------------------------------
126
127/// Error type returned by serde operations on [`Value`].
128///
129/// This is a string-based error type, separate from [`crate::Error`],
130/// because serde requires error types to support arbitrary messages
131/// via [`ser::Error::custom`] and [`de::Error::custom`]. The contained
132/// message is accessible directly through the public field.
133#[derive(Debug, Clone)]
134pub struct SerdeError(pub String);
135
136impl fmt::Display for SerdeError {
137    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
138        self.0.fmt(f)
139    }
140}
141
142impl std::error::Error for SerdeError {}
143
144impl ser::Error for SerdeError {
145    fn custom<T: fmt::Display>(msg: T) -> Self {
146        SerdeError(msg.to_string())
147    }
148}
149
150impl de::Error for SerdeError {
151    fn custom<T: fmt::Display>(msg: T) -> Self {
152        SerdeError(msg.to_string())
153    }
154}
155
156impl From<crate::Error> for SerdeError {
157    fn from(error: crate::Error) -> Self {
158        SerdeError(error.to_string())
159    }
160}
161
162// ---------------------------------------------------------------------------
163// Public API on Value
164// ---------------------------------------------------------------------------
165
166impl Value {
167    /// Serialize any [`Serialize`] value into a CBOR [`Value`].
168    ///
169    /// ```
170    /// use cbor_core::Value;
171    /// use serde::Serialize;
172    ///
173    /// #[derive(Serialize)]
174    /// struct Point { x: i32, y: i32 }
175    ///
176    /// let p = Point { x: 1, y: 2 };
177    /// let v = Value::serialized(&p).unwrap();
178    /// assert_eq!(v["x"].to_i32().unwrap(), 1);
179    /// assert_eq!(v["y"].to_i32().unwrap(), 2);
180    /// ```
181    pub fn serialized<T: ?Sized + Serialize>(value: &T) -> Result<Self, SerdeError> {
182        value.serialize(ValueSerializer)
183    }
184
185    /// Deserialize this [`Value`] into any [`Deserialize`] type.
186    ///
187    /// ```
188    /// use cbor_core::{Value, map};
189    /// use serde::Deserialize;
190    ///
191    /// #[derive(Deserialize, Debug, PartialEq)]
192    /// struct Point { x: i32, y: i32 }
193    ///
194    /// let v = map! { "x" => 1, "y" => 2 };
195    /// let p: Point = v.deserialized().unwrap();
196    /// assert_eq!(p, Point { x: 1, y: 2 });
197    /// ```
198    pub fn deserialized<'de, T: Deserialize<'de>>(&'de self) -> Result<T, SerdeError> {
199        T::deserialize(ValueDeserializer(self))
200    }
201}
202
203// ---------------------------------------------------------------------------
204// Serialize impl for Value
205// ---------------------------------------------------------------------------
206
207impl Serialize for Value {
208    fn serialize<S: ser::Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
209        match self {
210            Value::SimpleValue(sv) => match sv.data_type() {
211                crate::DataType::Null => serializer.serialize_unit(),
212                crate::DataType::Bool => serializer.serialize_bool(sv.to_bool().unwrap()),
213                _ => serializer.serialize_u8(sv.to_u8()),
214            },
215            Value::Unsigned(n) => serializer.serialize_u64(*n),
216            Value::Negative(n) => {
217                // actual value = -1 - n
218                if let Ok(v) = i64::try_from(*n).map(|v| !v) {
219                    serializer.serialize_i64(v)
220                } else {
221                    serializer.serialize_i128(!(*n as i128))
222                }
223            }
224            Value::Float(float) => serializer.serialize_f64(float.to_f64()),
225            Value::ByteString(b) => serializer.serialize_bytes(b),
226            Value::TextString(s) => serializer.serialize_str(s),
227            Value::Array(arr) => {
228                let mut seq = serializer.serialize_seq(Some(arr.len()))?;
229                for item in arr {
230                    seq.serialize_element(item)?;
231                }
232                seq.end()
233            }
234            Value::Map(map) => {
235                let mut m = serializer.serialize_map(Some(map.len()))?;
236                for (k, v) in map {
237                    m.serialize_entry(k, v)?;
238                }
239                m.end()
240            }
241            // Tags are transparent: serialize the inner content.
242            Value::Tag(_, content) => content.serialize(serializer),
243        }
244    }
245}
246
247// ---------------------------------------------------------------------------
248// Deserialize impl for Value
249// ---------------------------------------------------------------------------
250
251impl<'de> Deserialize<'de> for Value {
252    fn deserialize<D: de::Deserializer<'de>>(deserializer: D) -> Result<Self, D::Error> {
253        deserializer.deserialize_any(ValueVisitor)
254    }
255}
256
257struct ValueVisitor;
258
259macro_rules! visit {
260    ($method:ident, $type:ty) => {
261        fn $method<E>(self, v: $type) -> Result<Value, E> {
262            Ok(Value::from(v))
263        }
264    };
265}
266
267impl<'de> Visitor<'de> for ValueVisitor {
268    type Value = Value;
269
270    fn expecting(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
271        f.write_str("any CBOR-compatible value")
272    }
273
274    visit!(visit_bool, bool);
275
276    visit!(visit_i8, i8);
277    visit!(visit_i16, i16);
278    visit!(visit_i32, i32);
279    visit!(visit_i64, i64);
280    visit!(visit_i128, i128);
281
282    visit!(visit_u8, u8);
283    visit!(visit_u16, u16);
284    visit!(visit_u32, u32);
285    visit!(visit_u64, u64);
286    visit!(visit_u128, u128);
287
288    visit!(visit_f32, f32);
289    visit!(visit_f64, f64);
290
291    fn visit_char<E>(self, v: char) -> Result<Value, E> {
292        Ok(Value::from(v.to_string()))
293    }
294
295    visit!(visit_str, &str);
296    visit!(visit_string, String);
297
298    visit!(visit_bytes, &[u8]);
299    visit!(visit_byte_buf, Vec<u8>);
300
301    fn visit_none<E>(self) -> Result<Value, E> {
302        Ok(Value::null())
303    }
304
305    fn visit_some<D: de::Deserializer<'de>>(self, deserializer: D) -> Result<Value, D::Error> {
306        Deserialize::deserialize(deserializer)
307    }
308
309    fn visit_unit<E>(self) -> Result<Value, E> {
310        Ok(Value::null())
311    }
312
313    fn visit_seq<A: SeqAccess<'de>>(self, mut access: A) -> Result<Value, A::Error> {
314        let mut elements = Vec::with_capacity(access.size_hint().unwrap_or(0));
315        while let Some(elem) = access.next_element()? {
316            elements.push(elem);
317        }
318        Ok(Value::Array(elements))
319    }
320
321    fn visit_map<A: MapAccess<'de>>(self, mut access: A) -> Result<Value, A::Error> {
322        let mut map = BTreeMap::new();
323        while let Some((k, v)) = access.next_entry()? {
324            map.insert(k, v);
325        }
326        Ok(Value::Map(map))
327    }
328}
329
330// ---------------------------------------------------------------------------
331// ValueSerializer: Rust → Value
332// ---------------------------------------------------------------------------
333
334/// Serde `Serializer` that produces a CBOR [`Value`].
335struct ValueSerializer;
336
337macro_rules! serialize {
338    ($method:ident, $type:ty) => {
339        fn $method(self, v: $type) -> Result<Value, SerdeError> {
340            Ok(Value::from(v))
341        }
342    };
343}
344
345impl ser::Serializer for ValueSerializer {
346    type Ok = Value;
347    type Error = SerdeError;
348
349    type SerializeSeq = SeqBuilder;
350    type SerializeTuple = SeqBuilder;
351    type SerializeTupleStruct = SeqBuilder;
352    type SerializeTupleVariant = TupleVariantBuilder;
353    type SerializeMap = MapBuilder;
354    type SerializeStruct = MapBuilder;
355    type SerializeStructVariant = StructVariantBuilder;
356
357    serialize!(serialize_bool, bool);
358
359    serialize!(serialize_i8, i8);
360    serialize!(serialize_i16, i16);
361    serialize!(serialize_i32, i32);
362    serialize!(serialize_i64, i64);
363    serialize!(serialize_i128, i128);
364
365    serialize!(serialize_u8, u8);
366    serialize!(serialize_u16, u16);
367    serialize!(serialize_u32, u32);
368    serialize!(serialize_u64, u64);
369    serialize!(serialize_u128, u128);
370
371    serialize!(serialize_f32, f32);
372    serialize!(serialize_f64, f64);
373
374    fn serialize_char(self, v: char) -> Result<Value, SerdeError> {
375        Ok(Value::from(v.to_string()))
376    }
377
378    serialize!(serialize_str, &str);
379    serialize!(serialize_bytes, &[u8]);
380
381    fn serialize_none(self) -> Result<Value, SerdeError> {
382        Ok(Value::null())
383    }
384
385    fn serialize_some<T: ?Sized + Serialize>(self, value: &T) -> Result<Value, SerdeError> {
386        value.serialize(self)
387    }
388
389    fn serialize_unit(self) -> Result<Value, SerdeError> {
390        Ok(Value::null())
391    }
392
393    fn serialize_unit_struct(self, _name: &'static str) -> Result<Value, SerdeError> {
394        Ok(Value::null())
395    }
396
397    fn serialize_unit_variant(
398        self,
399        _name: &'static str,
400        _variant_index: u32,
401        variant: &'static str,
402    ) -> Result<Value, SerdeError> {
403        Ok(Value::from(variant))
404    }
405
406    fn serialize_newtype_struct<T: ?Sized + Serialize>(
407        self,
408        _name: &'static str,
409        value: &T,
410    ) -> Result<Value, SerdeError> {
411        value.serialize(self)
412    }
413
414    fn serialize_newtype_variant<T: ?Sized + Serialize>(
415        self,
416        _name: &'static str,
417        _variant_index: u32,
418        variant: &'static str,
419        value: &T,
420    ) -> Result<Value, SerdeError> {
421        Ok(Value::map([(variant, Value::serialized(value)?)]))
422    }
423
424    fn serialize_seq(self, len: Option<usize>) -> Result<SeqBuilder, SerdeError> {
425        Ok(SeqBuilder {
426            elements: Vec::with_capacity(len.unwrap_or(0)),
427        })
428    }
429
430    fn serialize_tuple(self, len: usize) -> Result<SeqBuilder, SerdeError> {
431        self.serialize_seq(Some(len))
432    }
433
434    fn serialize_tuple_struct(self, _name: &'static str, len: usize) -> Result<SeqBuilder, SerdeError> {
435        self.serialize_seq(Some(len))
436    }
437
438    fn serialize_tuple_variant(
439        self,
440        _name: &'static str,
441        _variant_index: u32,
442        variant: &'static str,
443        len: usize,
444    ) -> Result<TupleVariantBuilder, SerdeError> {
445        Ok(TupleVariantBuilder {
446            variant,
447            elements: Vec::with_capacity(len),
448        })
449    }
450
451    fn serialize_map(self, len: Option<usize>) -> Result<MapBuilder, SerdeError> {
452        let _ = len; // BTreeMap doesn't pre-allocate
453        Ok(MapBuilder {
454            entries: BTreeMap::new(),
455            next_key: None,
456        })
457    }
458
459    fn serialize_struct(self, _name: &'static str, len: usize) -> Result<MapBuilder, SerdeError> {
460        self.serialize_map(Some(len))
461    }
462
463    fn serialize_struct_variant(
464        self,
465        _name: &'static str,
466        _variant_index: u32,
467        variant: &'static str,
468        _len: usize,
469    ) -> Result<StructVariantBuilder, SerdeError> {
470        Ok(StructVariantBuilder {
471            variant,
472            entries: BTreeMap::new(),
473        })
474    }
475}
476
477// --- Serializer helpers ---
478
479struct SeqBuilder {
480    elements: Vec<Value>,
481}
482
483impl SerializeSeq for SeqBuilder {
484    type Ok = Value;
485    type Error = SerdeError;
486
487    fn serialize_element<T: ?Sized + Serialize>(&mut self, value: &T) -> Result<(), SerdeError> {
488        self.elements.push(Value::serialized(value)?);
489        Ok(())
490    }
491
492    fn end(self) -> Result<Value, SerdeError> {
493        Ok(Value::Array(self.elements))
494    }
495}
496
497impl ser::SerializeTuple for SeqBuilder {
498    type Ok = Value;
499    type Error = SerdeError;
500
501    fn serialize_element<T: ?Sized + Serialize>(&mut self, value: &T) -> Result<(), SerdeError> {
502        SerializeSeq::serialize_element(self, value)
503    }
504
505    fn end(self) -> Result<Value, SerdeError> {
506        SerializeSeq::end(self)
507    }
508}
509
510impl ser::SerializeTupleStruct for SeqBuilder {
511    type Ok = Value;
512    type Error = SerdeError;
513
514    fn serialize_field<T: ?Sized + Serialize>(&mut self, value: &T) -> Result<(), SerdeError> {
515        SerializeSeq::serialize_element(self, value)
516    }
517
518    fn end(self) -> Result<Value, SerdeError> {
519        SerializeSeq::end(self)
520    }
521}
522
523struct TupleVariantBuilder {
524    variant: &'static str,
525    elements: Vec<Value>,
526}
527
528impl ser::SerializeTupleVariant for TupleVariantBuilder {
529    type Ok = Value;
530    type Error = SerdeError;
531
532    fn serialize_field<T: ?Sized + Serialize>(&mut self, value: &T) -> Result<(), SerdeError> {
533        self.elements.push(Value::serialized(value)?);
534        Ok(())
535    }
536
537    fn end(self) -> Result<Value, SerdeError> {
538        Ok(Value::map([(self.variant, self.elements)]))
539    }
540}
541
542struct MapBuilder {
543    entries: BTreeMap<Value, Value>,
544    next_key: Option<Value>,
545}
546
547impl SerializeMap for MapBuilder {
548    type Ok = Value;
549    type Error = SerdeError;
550
551    fn serialize_key<T: ?Sized + Serialize>(&mut self, key: &T) -> Result<(), SerdeError> {
552        self.next_key = Some(Value::serialized(key)?);
553        Ok(())
554    }
555
556    fn serialize_value<T: ?Sized + Serialize>(&mut self, value: &T) -> Result<(), SerdeError> {
557        let key = self
558            .next_key
559            .take()
560            .ok_or_else(|| SerdeError("serialize_value called before serialize_key".into()))?;
561        self.entries.insert(key, Value::serialized(value)?);
562        Ok(())
563    }
564
565    fn end(self) -> Result<Value, SerdeError> {
566        Ok(Value::Map(self.entries))
567    }
568}
569
570impl ser::SerializeStruct for MapBuilder {
571    type Ok = Value;
572    type Error = SerdeError;
573
574    fn serialize_field<T: ?Sized + Serialize>(&mut self, key: &'static str, value: &T) -> Result<(), SerdeError> {
575        self.entries.insert(Value::from(key), Value::serialized(value)?);
576        Ok(())
577    }
578
579    fn end(self) -> Result<Value, SerdeError> {
580        Ok(Value::Map(self.entries))
581    }
582}
583
584struct StructVariantBuilder {
585    variant: &'static str,
586    entries: BTreeMap<Value, Value>,
587}
588
589impl ser::SerializeStructVariant for StructVariantBuilder {
590    type Ok = Value;
591    type Error = SerdeError;
592
593    fn serialize_field<T: ?Sized + Serialize>(&mut self, key: &'static str, value: &T) -> Result<(), SerdeError> {
594        self.entries.insert(Value::from(key), Value::serialized(value)?);
595        Ok(())
596    }
597
598    fn end(self) -> Result<Value, SerdeError> {
599        Ok(Value::map([(self.variant, self.entries)]))
600    }
601}
602
603// ---------------------------------------------------------------------------
604// ValueDeserializer: &Value → Rust
605// ---------------------------------------------------------------------------
606
607/// Serde `Deserializer` that reads from a CBOR [`Value`] reference.
608struct ValueDeserializer<'de>(&'de Value);
609
610macro_rules! deserialize {
611    ($method:ident, $visit:ident) => {
612        fn $method<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
613            visitor.$visit(self.0.try_into()?)
614        }
615    };
616}
617
618impl<'de> de::Deserializer<'de> for ValueDeserializer<'de> {
619    type Error = SerdeError;
620
621    fn deserialize_any<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
622        let this = self.0.peeled();
623        if let Value::SimpleValue(sv) = this {
624            if sv.data_type().is_null() {
625                visitor.visit_unit()
626            } else if let Ok(v) = sv.to_bool() {
627                visitor.visit_bool(v)
628            } else {
629                visitor.visit_u8(sv.to_u8())
630            }
631        } else if let Ok(v) = this.to_u64() {
632            visitor.visit_u64(v)
633        } else if let Ok(v) = this.to_i64() {
634            visitor.visit_i64(v)
635        } else if let Ok(v) = this.to_u128() {
636            visitor.visit_u128(v)
637        } else if let Ok(v) = this.to_i128() {
638            visitor.visit_i128(v)
639        } else if let Ok(v) = this.to_f32() {
640            visitor.visit_f32(v)
641        } else if let Ok(v) = this.to_f64() {
642            visitor.visit_f64(v)
643        } else if let Ok(v) = this.as_bytes() {
644            visitor.visit_borrowed_bytes(v)
645        } else if let Ok(v) = this.as_str() {
646            visitor.visit_borrowed_str(v)
647        } else {
648            match this.untagged() {
649                Value::Array(arr) => visitor.visit_seq(SeqAccessImpl(arr.iter())),
650                Value::Map(map) => visitor.visit_map(MapAccessImpl {
651                    iter: map.iter(),
652                    pending_value: None,
653                }),
654                _other => unreachable!(),
655            }
656        }
657    }
658
659    deserialize!(deserialize_bool, visit_bool);
660
661    deserialize!(deserialize_i8, visit_i8);
662    deserialize!(deserialize_i16, visit_i16);
663    deserialize!(deserialize_i32, visit_i32);
664    deserialize!(deserialize_i64, visit_i64);
665    deserialize!(deserialize_i128, visit_i128);
666
667    deserialize!(deserialize_u8, visit_u8);
668    deserialize!(deserialize_u16, visit_u16);
669    deserialize!(deserialize_u32, visit_u32);
670    deserialize!(deserialize_u64, visit_u64);
671    deserialize!(deserialize_u128, visit_u128);
672
673    fn deserialize_f32<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
674        visitor.visit_f32(self.0.to_f64()? as f32)
675    }
676
677    deserialize!(deserialize_f64, visit_f64);
678
679    fn deserialize_char<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
680        let s = self.0.as_str()?;
681        let mut chars = s.chars();
682        let ch = chars.next().ok_or_else(|| SerdeError("empty string for char".into()))?;
683        if chars.next().is_some() {
684            return Err(SerdeError("string contains more than one char".into()));
685        }
686        visitor.visit_char(ch)
687    }
688
689    deserialize!(deserialize_str, visit_borrowed_str);
690    deserialize!(deserialize_string, visit_borrowed_str);
691
692    deserialize!(deserialize_bytes, visit_borrowed_bytes);
693    deserialize!(deserialize_byte_buf, visit_borrowed_bytes);
694
695    fn deserialize_option<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
696        if self.0.untagged().data_type().is_null() {
697            visitor.visit_none()
698        } else {
699            visitor.visit_some(self)
700        }
701    }
702
703    fn deserialize_unit<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
704        if self.0.untagged().data_type().is_null() {
705            visitor.visit_unit()
706        } else {
707            Err(de::Error::custom(format!(
708                "expected null, got {}",
709                self.0.data_type().name()
710            )))
711        }
712    }
713
714    fn deserialize_unit_struct<V: Visitor<'de>>(self, _name: &'static str, visitor: V) -> Result<V::Value, SerdeError> {
715        self.deserialize_unit(visitor)
716    }
717
718    fn deserialize_newtype_struct<V: Visitor<'de>>(
719        self,
720        _name: &'static str,
721        visitor: V,
722    ) -> Result<V::Value, SerdeError> {
723        visitor.visit_newtype_struct(self)
724    }
725
726    fn deserialize_seq<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
727        match self.0.untagged() {
728            Value::Array(arr) => visitor.visit_seq(SeqAccessImpl(arr.iter())),
729            other => Err(de::Error::custom(format!(
730                "expected array, got {}",
731                other.data_type().name()
732            ))),
733        }
734    }
735
736    fn deserialize_tuple<V: Visitor<'de>>(self, _len: usize, visitor: V) -> Result<V::Value, SerdeError> {
737        self.deserialize_seq(visitor)
738    }
739
740    fn deserialize_tuple_struct<V: Visitor<'de>>(
741        self,
742        _name: &'static str,
743        _len: usize,
744        visitor: V,
745    ) -> Result<V::Value, SerdeError> {
746        self.deserialize_seq(visitor)
747    }
748
749    fn deserialize_map<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
750        match self.0.untagged() {
751            Value::Map(map) => visitor.visit_map(MapAccessImpl {
752                iter: map.iter(),
753                pending_value: None,
754            }),
755            other => Err(de::Error::custom(format!(
756                "expected map, got {}",
757                other.data_type().name()
758            ))),
759        }
760    }
761
762    fn deserialize_struct<V: Visitor<'de>>(
763        self,
764        _name: &'static str,
765        _fields: &'static [&'static str],
766        visitor: V,
767    ) -> Result<V::Value, SerdeError> {
768        self.deserialize_map(visitor)
769    }
770
771    fn deserialize_identifier<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
772        match self.0.untagged() {
773            Value::TextString(s) => visitor.visit_borrowed_str(s),
774            other => Err(de::Error::custom(format!(
775                "expected string identifier, got {}",
776                other.data_type().name()
777            ))),
778        }
779    }
780
781    fn deserialize_ignored_any<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, SerdeError> {
782        visitor.visit_unit()
783    }
784
785    fn deserialize_enum<V: Visitor<'de>>(
786        self,
787        _name: &'static str,
788        _variants: &'static [&'static str],
789        visitor: V,
790    ) -> Result<V::Value, SerdeError> {
791        match self.0.untagged() {
792            // Unit variant: "VariantName"
793            Value::TextString(variant) => visitor.visit_enum(de::value::StrDeserializer::new(variant)),
794
795            // Newtype / tuple / struct variant: { "VariantName": payload }
796            Value::Map(map) if map.len() == 1 => {
797                let (k, v) = map.iter().next().unwrap();
798                let variant = k.as_str()?;
799                visitor.visit_enum(EnumAccessImpl { variant, value: v })
800            }
801
802            other => Err(de::Error::custom(format!(
803                "expected string or single-entry map for enum, got {}",
804                other.data_type().name()
805            ))),
806        }
807    }
808}
809
810// ---------------------------------------------------------------------------
811// SeqAccess / MapAccess
812// ---------------------------------------------------------------------------
813
814struct SeqAccessImpl<'de>(std::slice::Iter<'de, Value>);
815
816impl<'de> SeqAccess<'de> for SeqAccessImpl<'de> {
817    type Error = SerdeError;
818
819    fn next_element_seed<T: DeserializeSeed<'de>>(&mut self, seed: T) -> Result<Option<T::Value>, SerdeError> {
820        match self.0.next() {
821            Some(v) => seed.deserialize(ValueDeserializer(v)).map(Some),
822            None => Ok(None),
823        }
824    }
825
826    fn size_hint(&self) -> Option<usize> {
827        Some(self.0.len())
828    }
829}
830
831struct MapAccessImpl<'de> {
832    iter: std::collections::btree_map::Iter<'de, Value, Value>,
833    pending_value: Option<&'de Value>,
834}
835
836impl<'de> MapAccess<'de> for MapAccessImpl<'de> {
837    type Error = SerdeError;
838
839    fn next_key_seed<K: DeserializeSeed<'de>>(&mut self, seed: K) -> Result<Option<K::Value>, SerdeError> {
840        match self.iter.next() {
841            Some((k, v)) => {
842                self.pending_value = Some(v);
843                seed.deserialize(ValueDeserializer(k)).map(Some)
844            }
845            None => Ok(None),
846        }
847    }
848
849    fn next_value_seed<V: DeserializeSeed<'de>>(&mut self, seed: V) -> Result<V::Value, SerdeError> {
850        let v = self
851            .pending_value
852            .take()
853            .ok_or_else(|| SerdeError("next_value_seed called before next_key_seed".into()))?;
854        seed.deserialize(ValueDeserializer(v))
855    }
856
857    fn size_hint(&self) -> Option<usize> {
858        Some(self.iter.len())
859    }
860}
861
862// ---------------------------------------------------------------------------
863// EnumAccess / VariantAccess
864// ---------------------------------------------------------------------------
865
866struct EnumAccessImpl<'de> {
867    variant: &'de str,
868    value: &'de Value,
869}
870
871impl<'de> de::EnumAccess<'de> for EnumAccessImpl<'de> {
872    type Error = SerdeError;
873    type Variant = VariantAccessImpl<'de>;
874
875    fn variant_seed<V: DeserializeSeed<'de>>(self, seed: V) -> Result<(V::Value, Self::Variant), SerdeError> {
876        let variant = seed.deserialize(de::value::StrDeserializer::<SerdeError>::new(self.variant))?;
877        Ok((variant, VariantAccessImpl(self.value)))
878    }
879}
880
881struct VariantAccessImpl<'de>(&'de Value);
882
883impl<'de> de::VariantAccess<'de> for VariantAccessImpl<'de> {
884    type Error = SerdeError;
885
886    fn unit_variant(self) -> Result<(), SerdeError> {
887        if self.0.untagged().data_type().is_null() {
888            Ok(())
889        } else {
890            Err(SerdeError(format!(
891                "expected null for unit variant, got {}",
892                self.0.data_type().name()
893            )))
894        }
895    }
896
897    fn newtype_variant_seed<T: DeserializeSeed<'de>>(self, seed: T) -> Result<T::Value, SerdeError> {
898        seed.deserialize(ValueDeserializer(self.0))
899    }
900
901    fn tuple_variant<V: Visitor<'de>>(self, _len: usize, visitor: V) -> Result<V::Value, SerdeError> {
902        ValueDeserializer(self.0).deserialize_seq(visitor)
903    }
904
905    fn struct_variant<V: Visitor<'de>>(
906        self,
907        _fields: &'static [&'static str],
908        visitor: V,
909    ) -> Result<V::Value, SerdeError> {
910        ValueDeserializer(self.0).deserialize_map(visitor)
911    }
912}
913
914// ---------------------------------------------------------------------------
915// Tests
916// ---------------------------------------------------------------------------
917
918#[cfg(test)]
919mod tests {
920    use super::*;
921    use crate::{array, map};
922
923    // --- Round-trip: primitives ---
924
925    #[test]
926    fn round_trip_bool() {
927        let v = Value::serialized(&true).unwrap();
928        assert!(v.to_bool().unwrap());
929        assert!(v.deserialized::<bool>().unwrap());
930
931        let v = Value::serialized(&false).unwrap();
932        assert!(!v.deserialized::<bool>().unwrap());
933    }
934
935    #[test]
936    fn round_trip_unsigned() {
937        let v = Value::serialized(&42_u32).unwrap();
938        assert_eq!(v.to_u64().unwrap(), 42);
939        assert_eq!(v.deserialized::<u32>().unwrap(), 42);
940    }
941
942    #[test]
943    fn round_trip_signed_positive() {
944        let v = Value::serialized(&100_i64).unwrap();
945        assert_eq!(v.deserialized::<i64>().unwrap(), 100);
946    }
947
948    #[test]
949    fn round_trip_signed_negative() {
950        let v = Value::serialized(&-42_i32).unwrap();
951        assert_eq!(v.deserialized::<i32>().unwrap(), -42);
952    }
953
954    #[test]
955    fn round_trip_float() {
956        let v = Value::serialized(&3.42_f64).unwrap();
957        assert_eq!(v.deserialized::<f64>().unwrap(), 3.42);
958    }
959
960    #[test]
961    fn round_trip_string() {
962        let v = Value::serialized("hello").unwrap();
963        assert_eq!(v.as_str().unwrap(), "hello");
964        assert_eq!(v.deserialized::<String>().unwrap(), "hello");
965    }
966
967    #[test]
968    fn round_trip_bytes() {
969        let data = vec![1_u8, 2, 3];
970        let v = Value::serialized(&serde_bytes::Bytes::new(&data)).unwrap();
971        assert_eq!(v.as_bytes().unwrap(), &[1, 2, 3]);
972        let back: serde_bytes::ByteBuf = v.deserialized().unwrap();
973        assert_eq!(back.as_ref(), &[1, 2, 3]);
974    }
975
976    #[test]
977    fn round_trip_none() {
978        let v = Value::serialized(&Option::<i32>::None).unwrap();
979        assert!(v.data_type().is_null());
980        assert_eq!(v.deserialized::<Option<i32>>().unwrap(), None);
981    }
982
983    #[test]
984    fn round_trip_some() {
985        let v = Value::serialized(&Some(42_u32)).unwrap();
986        assert_eq!(v.deserialized::<Option<u32>>().unwrap(), Some(42));
987    }
988
989    // --- Round-trip: collections ---
990
991    #[test]
992    fn round_trip_vec() {
993        let v = Value::serialized(&vec![1_u32, 2, 3]).unwrap();
994        assert_eq!(v.deserialized::<Vec<u32>>().unwrap(), vec![1, 2, 3]);
995    }
996
997    #[test]
998    fn round_trip_map() {
999        let mut m = std::collections::BTreeMap::new();
1000        m.insert("a".to_string(), 1_u32);
1001        m.insert("b".to_string(), 2);
1002        let v = Value::serialized(&m).unwrap();
1003        let back: std::collections::BTreeMap<String, u32> = v.deserialized().unwrap();
1004        assert_eq!(back, m);
1005    }
1006
1007    // --- Round-trip: structs ---
1008
1009    #[test]
1010    fn round_trip_struct() {
1011        #[derive(Serialize, Deserialize, Debug, PartialEq)]
1012        struct Point {
1013            x: i32,
1014            y: i32,
1015        }
1016
1017        let p = Point { x: 10, y: -20 };
1018        let v = Value::serialized(&p).unwrap();
1019        assert_eq!(v["x"].to_i32().unwrap(), 10);
1020        assert_eq!(v["y"].to_i32().unwrap(), -20);
1021        let back: Point = v.deserialized().unwrap();
1022        assert_eq!(back, p);
1023    }
1024
1025    #[test]
1026    fn round_trip_nested_struct() {
1027        #[derive(Serialize, Deserialize, Debug, PartialEq)]
1028        struct Inner {
1029            value: String,
1030        }
1031        #[derive(Serialize, Deserialize, Debug, PartialEq)]
1032        struct Outer {
1033            name: String,
1034            inner: Inner,
1035        }
1036
1037        let o = Outer {
1038            name: "test".into(),
1039            inner: Inner { value: "nested".into() },
1040        };
1041        let v = Value::serialized(&o).unwrap();
1042        let back: Outer = v.deserialized().unwrap();
1043        assert_eq!(back, o);
1044    }
1045
1046    // --- Round-trip: enums ---
1047
1048    #[test]
1049    fn round_trip_unit_variant() {
1050        #[derive(Serialize, Deserialize, Debug, PartialEq)]
1051        enum Color {
1052            Red,
1053            Green,
1054            Blue,
1055        }
1056
1057        let v = Value::serialized(&Color::Green).unwrap();
1058        assert_eq!(v.as_str().unwrap(), "Green");
1059        let back: Color = v.deserialized().unwrap();
1060        assert_eq!(back, Color::Green);
1061    }
1062
1063    #[test]
1064    fn round_trip_newtype_variant() {
1065        #[derive(Serialize, Deserialize, Debug, PartialEq)]
1066        enum Shape {
1067            Circle(f64),
1068            Square(f64),
1069        }
1070
1071        let v = Value::serialized(&Shape::Circle(2.5)).unwrap();
1072        let back: Shape = v.deserialized().unwrap();
1073        assert_eq!(back, Shape::Circle(2.5));
1074    }
1075
1076    #[test]
1077    fn round_trip_struct_variant() {
1078        #[derive(Serialize, Deserialize, Debug, PartialEq)]
1079        enum Message {
1080            Quit,
1081            Move { x: i32, y: i32 },
1082        }
1083
1084        let v = Value::serialized(&Message::Move { x: 1, y: 2 }).unwrap();
1085        let back: Message = v.deserialized().unwrap();
1086        assert_eq!(back, Message::Move { x: 1, y: 2 });
1087    }
1088
1089    #[test]
1090    fn round_trip_tuple_variant() {
1091        #[derive(Serialize, Deserialize, Debug, PartialEq)]
1092        enum Pair {
1093            Two(i32, i32),
1094        }
1095
1096        let v = Value::serialized(&Pair::Two(3, 4)).unwrap();
1097        let back: Pair = v.deserialized().unwrap();
1098        assert_eq!(back, Pair::Two(3, 4));
1099    }
1100
1101    // --- Deserialize from hand-built Value ---
1102
1103    #[test]
1104    fn deserialize_hand_built() {
1105        #[derive(Deserialize, Debug, PartialEq)]
1106        struct Record {
1107            id: u64,
1108            name: String,
1109            active: bool,
1110        }
1111
1112        let v = map! {
1113            "id" => 42,
1114            "name" => "alice",
1115            "active" => true,
1116        };
1117
1118        let r: Record = v.deserialized().unwrap();
1119        assert_eq!(
1120            r,
1121            Record {
1122                id: 42,
1123                name: "alice".into(),
1124                active: true,
1125            }
1126        );
1127    }
1128
1129    // --- Serialize Value itself ---
1130
1131    #[test]
1132    fn serialize_value_null() {
1133        let v = Value::null();
1134        let json = serde_json::to_string(&v).unwrap();
1135        assert_eq!(json, "null");
1136    }
1137
1138    #[test]
1139    fn serialize_value_integer() {
1140        let v = Value::from(42_u64);
1141        let json = serde_json::to_string(&v).unwrap();
1142        assert_eq!(json, "42");
1143    }
1144
1145    #[test]
1146    fn serialize_value_negative() {
1147        let v = Value::from(-10_i64);
1148        let json = serde_json::to_string(&v).unwrap();
1149        assert_eq!(json, "-10");
1150    }
1151
1152    #[test]
1153    fn serialize_value_array() {
1154        let v = array![1, 2, 3];
1155        let json = serde_json::to_string(&v).unwrap();
1156        assert_eq!(json, "[1,2,3]");
1157    }
1158
1159    #[test]
1160    fn serialize_value_map() {
1161        let v = map! { "a" => 1 };
1162        let json = serde_json::to_string(&v).unwrap();
1163        assert_eq!(json, "{\"a\":1}");
1164    }
1165
1166    // --- Tags are transparent ---
1167
1168    #[test]
1169    fn tagged_value_transparent_deserialize() {
1170        // Tag wrapping an integer should deserialize as if untagged.
1171        let v = Value::tag(42, 100_u64);
1172        let n: u64 = v.deserialized().unwrap();
1173        assert_eq!(n, 100);
1174    }
1175
1176    #[test]
1177    fn tagged_value_transparent_serialize() {
1178        let v = Value::tag(42, 100_u64);
1179        let json = serde_json::to_string(&v).unwrap();
1180        assert_eq!(json, "100");
1181    }
1182
1183    // --- Edge cases ---
1184
1185    #[test]
1186    fn large_negative_i128() {
1187        let big = i64::MIN as i128 - 1;
1188        let v = Value::serialized(&big).unwrap();
1189        let back: i128 = v.deserialized().unwrap();
1190        assert_eq!(back, big);
1191    }
1192
1193    #[test]
1194    fn unit_type() {
1195        let v = Value::serialized(&()).unwrap();
1196        assert!(v.data_type().is_null());
1197        v.deserialized::<()>().unwrap();
1198    }
1199
1200    #[test]
1201    fn char_round_trip() {
1202        let v = Value::serialized(&'Z').unwrap();
1203        assert_eq!(v.deserialized::<char>().unwrap(), 'Z');
1204    }
1205
1206    #[test]
1207    fn empty_vec() {
1208        let v = Value::serialized(&Vec::<i32>::new()).unwrap();
1209        assert_eq!(v.deserialized::<Vec<i32>>().unwrap(), Vec::<i32>::new());
1210    }
1211
1212    #[test]
1213    fn empty_map() {
1214        let v = Value::serialized(&std::collections::BTreeMap::<String, i32>::new()).unwrap();
1215        let back: std::collections::BTreeMap<String, i32> = v.deserialized().unwrap();
1216        assert!(back.is_empty());
1217    }
1218
1219    #[test]
1220    fn deserialize_error_type_mismatch() {
1221        let v = Value::from("not a number");
1222        let result = v.deserialized::<u32>();
1223        assert!(result.is_err());
1224    }
1225
1226    #[test]
1227    fn deserialize_error_overflow() {
1228        let v = Value::from(1000_u64);
1229        let result = v.deserialized::<u8>();
1230        assert!(result.is_err());
1231    }
1232
1233    #[test]
1234    fn optional_field() {
1235        #[derive(Serialize, Deserialize, Debug, PartialEq)]
1236        struct Config {
1237            name: String,
1238            port: Option<u16>,
1239        }
1240
1241        let with = Value::serialized(&Config {
1242            name: "srv".into(),
1243            port: Some(8080),
1244        })
1245        .unwrap();
1246        let back: Config = with.deserialized().unwrap();
1247        assert_eq!(back.port, Some(8080));
1248
1249        let without = Value::serialized(&Config {
1250            name: "srv".into(),
1251            port: None,
1252        })
1253        .unwrap();
1254        let back: Config = without.deserialized().unwrap();
1255        assert_eq!(back.port, None);
1256    }
1257
1258    #[test]
1259    fn tuple() {
1260        let v = Value::serialized(&(1_u32, "hello", true)).unwrap();
1261        let back: (u32, String, bool) = v.deserialized().unwrap();
1262        assert_eq!(back, (1, "hello".into(), true));
1263    }
1264
1265    // --- SerdeError public field ---
1266
1267    #[test]
1268    fn serde_error_message_accessible() {
1269        let v = Value::from("not a number");
1270        let err = v.deserialized::<u32>().unwrap_err();
1271        // The public String field is directly readable.
1272        assert!(!err.0.is_empty());
1273        assert_eq!(err.to_string(), err.0);
1274    }
1275
1276    // --- Deserialize Value from JSON (proves Deserialize impl works) ---
1277
1278    #[test]
1279    fn deserialize_value_from_json() {
1280        let v: Value = serde_json::from_str(r#"{"key": [1, 2, 3]}"#).unwrap();
1281        let arr = v["key"].as_array().unwrap();
1282        assert_eq!(arr.len(), 3);
1283        assert_eq!(arr[0].to_u32().unwrap(), 1);
1284    }
1285}