sonic_rs/lazyvalue/
de.rs

1use std::{marker::PhantomData, mem::MaybeUninit};
2
3use ::serde::{de, de::Visitor, Deserialize, Deserializer};
4use faststr::FastStr;
5
6use super::{owned::OwnedLazyValue, value::LazyValue};
7use crate::lazyvalue::value::HasEsc;
8
9impl<'de: 'a, 'a> Deserialize<'de> for LazyValue<'a> {
10    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
11    where
12        D: Deserializer<'de>,
13    {
14        struct LazyValueVisitor<'a> {
15            _marker: PhantomData<&'a ()>,
16        }
17
18        impl<'de: 'a, 'a> Visitor<'de> for LazyValueVisitor<'a> {
19            type Value = LazyValue<'a>;
20
21            fn expecting(&self, formatter: &mut std::fmt::Formatter) -> std::fmt::Result {
22                write!(formatter, "any valid JSON value")
23            }
24
25            // NOTE: only used for visit the str that has escaped chars
26            fn visit_str<E>(self, v: &str) -> Result<Self::Value, E>
27            where
28                E: de::Error,
29            {
30                Ok(LazyValue::new(FastStr::new(v).into(), HasEsc::Yes))
31            }
32
33            fn visit_borrowed_str<E>(self, v: &'de str) -> Result<Self::Value, E>
34            where
35                E: de::Error,
36            {
37                Ok(LazyValue::new(v.as_bytes().into(), HasEsc::None))
38            }
39        }
40
41        let visit = LazyValueVisitor {
42            _marker: PhantomData,
43        };
44        deserializer.deserialize_newtype_struct(super::TOKEN, visit)
45    }
46}
47
48impl<'de> Deserialize<'de> for OwnedLazyValue {
49    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
50    where
51        D: Deserializer<'de>,
52    {
53        struct OwnedVisitor;
54
55        let visit = OwnedVisitor;
56
57        impl<'de> Visitor<'de> for OwnedVisitor {
58            type Value = OwnedLazyValue;
59
60            fn expecting(&self, formatter: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
61                formatter.write_str("expect a valid json")
62            }
63
64            fn visit_bytes<E>(self, value_binary: &[u8]) -> std::result::Result<Self::Value, E>
65            where
66                E: de::Error,
67            {
68                // we pass the value from value_binary
69                unsafe {
70                    assert!(
71                        value_binary.len() == std::mem::size_of::<Self::Value>(),
72                        "invalid value size {}",
73                        value_binary.len()
74                    );
75                    let mut dom: MaybeUninit<Self::Value> = MaybeUninit::zeroed();
76                    std::ptr::copy_nonoverlapping(
77                        value_binary.as_ptr() as *const Self::Value,
78                        dom.as_mut_ptr(),
79                        1,
80                    );
81                    Ok(dom.assume_init())
82                }
83            }
84        }
85
86        deserializer.deserialize_newtype_struct(super::OWNED_LAZY_VALUE_TOKEN, visit)
87    }
88}