Skip to main content

messagepack_serde/value/
value_owned.rs

1use super::number::Number;
2use super::value_ref::ValueRef;
3use alloc::string::{String, ToString};
4use alloc::vec::Vec;
5use messagepack_core::extension::{ExtensionOwned, ExtensionRef};
6use serde::{de::Visitor, ser::SerializeMap};
7
8/// Owned representation of any MessagePack value.
9#[derive(Debug, Clone, PartialEq, PartialOrd)]
10pub enum Value {
11    /// Represents nil format.
12    Nil,
13    /// Represents bool format family.
14    Bool(bool),
15    /// Represents `bin 8`, `bin 16` and `bin 32`.
16    Bin(Vec<u8>),
17    /// Represents ext format family as owned bytes.
18    Extension(ExtensionOwned),
19    /// Represents int format family and float format family.
20    Number(Number),
21    /// Represents str format family.
22    String(String),
23    /// Represents array format family.
24    Array(Vec<Value>),
25    /// Represents map format family.
26    Map(Vec<(Value, Value)>),
27}
28
29impl Value {
30    /// Returns true if the `Value` is nil.
31    pub fn is_nil(&self) -> bool {
32        matches!(self, Value::Nil)
33    }
34
35    /// If the `Value` is boolean, returns contained value.
36    pub fn as_bool(&self) -> Option<bool> {
37        match self {
38            Value::Bool(v) => Some(*v),
39            _ => None,
40        }
41    }
42
43    /// If the `Value` is bin, returns contained slice.
44    pub fn as_bin(&self) -> Option<&[u8]> {
45        match self {
46            Value::Bin(v) => Some(v.as_slice()),
47            _ => None,
48        }
49    }
50
51    /// If the `Value` is ext, returns `(type, data)` as tuple.
52    pub fn as_extension(&self) -> Option<ExtensionRef<'_>> {
53        match self {
54            Value::Extension(ext) => Some(ext.as_ref()),
55            _ => None,
56        }
57    }
58
59    /// If the `Value` is number, returns contained value.
60    pub fn as_number(&self) -> Option<Number> {
61        match self {
62            Value::Number(v) => Some(*v),
63            _ => None,
64        }
65    }
66
67    /// If the `Value` is str, returns contained slice.
68    pub fn as_string(&self) -> Option<&str> {
69        match self {
70            Value::String(v) => Some(v.as_str()),
71            _ => None,
72        }
73    }
74
75    /// If the `Value` is array, returns contained slice.
76    pub fn as_array(&self) -> Option<&[Value]> {
77        match self {
78            Value::Array(v) => Some(v.as_slice()),
79            _ => None,
80        }
81    }
82
83    /// If the `Value` is map, returns contained slice of pairs.
84    pub fn as_map(&self) -> Option<&[(Value, Value)]> {
85        match self {
86            Value::Map(v) => Some(v.as_slice()),
87            _ => None,
88        }
89    }
90}
91
92impl serde::Serialize for Value {
93    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
94    where
95        S: serde::Serializer,
96    {
97        match self {
98            Value::Nil => serializer.serialize_none(),
99            Value::Bool(v) => serializer.serialize_bool(*v),
100            Value::Bin(b) => serializer.serialize_bytes(b),
101            Value::Extension(ext) => {
102                crate::extension::ext_ref::serialize(&ext.as_ref(), serializer)
103            }
104            Value::Number(n) => n.serialize(serializer),
105            Value::String(s) => serializer.serialize_str(s),
106            Value::Array(vs) => vs.serialize(serializer),
107            Value::Map(items) => {
108                let mut map = serializer.serialize_map(Some(items.len()))?;
109                for (k, v) in items.iter() {
110                    map.serialize_entry(k, v)?;
111                }
112                map.end()
113            }
114        }
115    }
116}
117
118impl<'de> serde::Deserialize<'de> for Value {
119    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
120    where
121        D: serde::Deserializer<'de>,
122    {
123        struct ValueVisitor;
124        impl<'de> Visitor<'de> for ValueVisitor {
125            type Value = Value;
126            fn expecting(&self, f: &mut core::fmt::Formatter) -> core::fmt::Result {
127                f.write_str("expect valid messagepack")
128            }
129
130            fn visit_bool<E>(self, v: bool) -> Result<Self::Value, E>
131            where
132                E: serde::de::Error,
133            {
134                Ok(Value::Bool(v))
135            }
136
137            fn visit_u64<E>(self, v: u64) -> Result<Self::Value, E>
138            where
139                E: serde::de::Error,
140            {
141                Ok(Value::from(v))
142            }
143
144            fn visit_i64<E>(self, v: i64) -> Result<Self::Value, E>
145            where
146                E: serde::de::Error,
147            {
148                Ok(Value::from(v))
149            }
150
151            fn visit_f32<E>(self, v: f32) -> Result<Self::Value, E>
152            where
153                E: serde::de::Error,
154            {
155                Ok(Value::from(v))
156            }
157            fn visit_f64<E>(self, v: f64) -> Result<Self::Value, E>
158            where
159                E: serde::de::Error,
160            {
161                Ok(Value::from(v))
162            }
163
164            fn visit_str<E>(self, v: &str) -> Result<Self::Value, E>
165            where
166                E: serde::de::Error,
167            {
168                Ok(Value::from(v))
169            }
170
171            fn visit_string<E>(self, v: String) -> Result<Self::Value, E>
172            where
173                E: serde::de::Error,
174            {
175                Ok(Value::from(v))
176            }
177
178            fn visit_none<E>(self) -> Result<Self::Value, E>
179            where
180                E: serde::de::Error,
181            {
182                Ok(Value::Nil)
183            }
184            fn visit_unit<E>(self) -> Result<Self::Value, E>
185            where
186                E: serde::de::Error,
187            {
188                Ok(Value::Nil)
189            }
190
191            fn visit_bytes<E>(self, v: &[u8]) -> Result<Self::Value, E>
192            where
193                E: serde::de::Error,
194            {
195                Ok(Value::Bin(v.to_vec()))
196            }
197
198            fn visit_byte_buf<E>(self, v: Vec<u8>) -> Result<Self::Value, E>
199            where
200                E: serde::de::Error,
201            {
202                Ok(Value::Bin(v))
203            }
204
205            fn visit_newtype_struct<D>(self, deserializer: D) -> Result<Self::Value, D::Error>
206            where
207                D: serde::Deserializer<'de>,
208            {
209                let ext = crate::extension::ext_owned::deserialize(deserializer)?;
210                Ok(Value::Extension(ext))
211            }
212
213            fn visit_seq<A>(self, mut seq: A) -> Result<Self::Value, A::Error>
214            where
215                A: serde::de::SeqAccess<'de>,
216            {
217                let mut buf =
218                    Vec::with_capacity(super::cautiously_size_hint::<Value>(seq.size_hint()));
219
220                while let Some(v) = seq.next_element::<Value>()? {
221                    buf.push(v);
222                }
223                Ok(Value::Array(buf))
224            }
225
226            fn visit_map<A>(self, mut map: A) -> Result<Self::Value, A::Error>
227            where
228                A: serde::de::MapAccess<'de>,
229            {
230                let mut buf = Vec::with_capacity(super::cautiously_size_hint::<(Value, Value)>(
231                    map.size_hint(),
232                ));
233
234                while let Some(v) = map.next_entry::<Value, Value>()? {
235                    buf.push(v);
236                }
237                Ok(Value::Map(buf))
238            }
239        }
240        deserializer.deserialize_any(ValueVisitor)
241    }
242}
243
244impl From<()> for Value {
245    fn from(_: ()) -> Self {
246        Value::Nil
247    }
248}
249
250impl From<bool> for Value {
251    fn from(v: bool) -> Self {
252        Value::Bool(v)
253    }
254}
255
256impl From<u8> for Value {
257    fn from(v: u8) -> Self {
258        Value::Number(Number::from(v))
259    }
260}
261impl From<u16> for Value {
262    fn from(v: u16) -> Self {
263        Value::Number(Number::from(v))
264    }
265}
266impl From<u32> for Value {
267    fn from(v: u32) -> Self {
268        Value::Number(Number::from(v))
269    }
270}
271impl From<u64> for Value {
272    fn from(v: u64) -> Self {
273        Value::Number(Number::from(v))
274    }
275}
276
277impl From<i8> for Value {
278    fn from(v: i8) -> Self {
279        Value::Number(Number::from(v))
280    }
281}
282impl From<i16> for Value {
283    fn from(v: i16) -> Self {
284        Value::Number(Number::from(v))
285    }
286}
287impl From<i32> for Value {
288    fn from(v: i32) -> Self {
289        Value::Number(Number::from(v))
290    }
291}
292impl From<i64> for Value {
293    fn from(v: i64) -> Self {
294        Value::Number(Number::from(v))
295    }
296}
297
298impl From<f32> for Value {
299    fn from(v: f32) -> Self {
300        Value::Number(Number::Float(v.into()))
301    }
302}
303impl From<f64> for Value {
304    fn from(v: f64) -> Self {
305        Value::Number(Number::Float(v))
306    }
307}
308
309impl From<Number> for Value {
310    fn from(v: Number) -> Self {
311        Value::Number(v)
312    }
313}
314
315impl TryFrom<usize> for Value {
316    type Error = core::num::TryFromIntError;
317    fn try_from(value: usize) -> Result<Self, Self::Error> {
318        Number::try_from(value).map(Self::from)
319    }
320}
321
322impl TryFrom<isize> for Value {
323    type Error = core::num::TryFromIntError;
324    fn try_from(value: isize) -> Result<Self, Self::Error> {
325        Number::try_from(value).map(Self::from)
326    }
327}
328
329impl From<&str> for Value {
330    fn from(v: &str) -> Self {
331        Value::String(v.to_string())
332    }
333}
334impl From<String> for Value {
335    fn from(v: String) -> Self {
336        Value::String(v)
337    }
338}
339impl From<&[u8]> for Value {
340    fn from(v: &[u8]) -> Self {
341        Value::Bin(v.to_vec())
342    }
343}
344impl From<Vec<u8>> for Value {
345    fn from(v: Vec<u8>) -> Self {
346        Value::Bin(v)
347    }
348}
349
350impl From<ExtensionOwned> for Value {
351    fn from(v: ExtensionOwned) -> Self {
352        Value::Extension(v)
353    }
354}
355
356impl From<ValueRef<'_>> for Value {
357    fn from(v: ValueRef<'_>) -> Self {
358        match v {
359            ValueRef::Nil => Value::Nil,
360            ValueRef::Bool(b) => Value::Bool(b),
361            ValueRef::Bin(b) => Value::Bin(b.to_vec()),
362            ValueRef::Extension(ext) => Value::Extension(ext.into()),
363            ValueRef::Number(n) => Value::Number(n),
364            ValueRef::String(s) => Value::String(s.to_string()),
365            ValueRef::Array(items) => Value::Array(items.into_iter().map(Value::from).collect()),
366            ValueRef::Map(items) => Value::Map(
367                items
368                    .into_iter()
369                    .map(|(k, v)| (Value::from(k), Value::from(v)))
370                    .collect(),
371            ),
372        }
373    }
374}
375
376#[cfg(test)]
377mod tests {
378    use super::*;
379    use crate::{from_slice, to_slice};
380
381    #[test]
382    fn owned_roundtrip_primitives() {
383        let cases = [
384            Value::Nil,
385            Value::Bool(true),
386            Value::Number(Number::from(7u64)),
387            Value::Number(Number::from(-3i64)),
388            Value::Number(Number::Float(1.25)),
389            Value::String("hi".to_string()),
390            Value::Bin(vec![0x01, 0x02]),
391        ];
392        for v in cases.iter() {
393            let mut buf = [0u8; 32];
394            let len = to_slice(v, &mut buf).unwrap();
395            let decoded = from_slice::<Value>(&buf[..len]).unwrap();
396            assert_eq!(&decoded, v);
397        }
398    }
399
400    #[test]
401    fn owned_nested_roundtrip() {
402        let v = Value::Array(vec![
403            Value::Map(vec![
404                (Value::String("k".into()), Value::Bool(false)),
405                (Value::Number(1u64.into()), Value::String("v".into())),
406            ]),
407            Value::Extension(ExtensionOwned {
408                r#type: 1,
409                data: vec![0x12, 0x34],
410            }),
411        ]);
412        let mut buf = [0u8; 128];
413        let len = to_slice(&v, &mut buf).unwrap();
414        let decoded = from_slice::<Value>(&buf[..len]).unwrap();
415        assert_eq!(decoded, v);
416    }
417}
418
419#[cfg(all(test, feature = "std"))]
420mod reader_tests {
421    use super::*;
422    use crate::from_reader;
423
424    #[test]
425    fn value_owned_from_reader_str_and_bin() {
426        // fixstr "hi"
427        let mut r1 = std::io::Cursor::new([0xa2, 0x68, 0x69]);
428        let v1: Value = from_reader(&mut r1).unwrap();
429        assert_eq!(v1.as_string(), Some("hi"));
430
431        // bin8 [0x01, 0x02, 0x03]
432        let mut r2 = std::io::Cursor::new([0xc4, 0x03, 0x01, 0x02, 0x03]);
433        let v2: Value = from_reader(&mut r2).unwrap();
434        assert_eq!(v2.as_bin(), Some(&[1u8, 2, 3][..]));
435    }
436}