1use serde::de::{self, DeserializeOwned, Deserializer, MapAccess, SeqAccess, Visitor};
30use std::borrow::Cow;
31use std::collections::HashSet;
32use std::fmt;
33
34#[cfg(feature = "simd")]
39pub const BACKEND_ID: &str = "simd-json";
40#[cfg(not(feature = "simd"))]
42pub const BACKEND_ID: &str = "serde_json";
43
44#[derive(Debug)]
53pub(crate) struct DecodeError {
54 pub(crate) is_data: bool,
59 msg: String,
60}
61
62impl fmt::Display for DecodeError {
63 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
64 f.write_str(&self.msg)
65 }
66}
67
68impl From<serde_json::Error> for DecodeError {
69 fn from(e: serde_json::Error) -> Self {
70 DecodeError {
71 is_data: e.is_data(),
72 msg: e.to_string(),
73 }
74 }
75}
76
77#[cfg(not(feature = "simd"))]
81#[inline]
82pub(crate) fn decode_one<T: DeserializeOwned>(bytes: &[u8]) -> Result<T, DecodeError> {
83 serde_json::from_slice(bytes).map_err(DecodeError::from)
84}
85
86#[cfg(feature = "simd")]
93thread_local! {
94 static SIMD: std::cell::RefCell<(Vec<u8>, simd_json::Buffers)> =
95 std::cell::RefCell::new((Vec::new(), simd_json::Buffers::new(0)));
96}
97
98#[cfg(feature = "simd")]
106#[inline]
107pub(crate) fn decode_one<T: DeserializeOwned>(bytes: &[u8]) -> Result<T, DecodeError> {
108 SIMD.with(|cell| {
109 let (buf, buffers) = &mut *cell.borrow_mut();
110 buf.clear();
111 buf.extend_from_slice(bytes);
112 simd_json::serde::from_slice_with_buffers::<T>(buf.as_mut_slice(), buffers).map_err(|e| {
113 DecodeError {
114 is_data: false,
115 msg: e.to_string(),
116 }
117 })
118 })
119}
120
121pub(crate) fn check_no_duplicate_keys(bytes: &[u8]) -> Result<(), DecodeError> {
129 serde_json::from_slice::<DupGuard>(bytes)
132 .map(|_| ())
133 .map_err(DecodeError::from)
134}
135
136struct DupGuard;
140
141impl<'de> serde::Deserialize<'de> for DupGuard {
142 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
143 where
144 D: Deserializer<'de>,
145 {
146 deserializer.deserialize_any(DupVisitor)
147 }
148}
149
150struct DupVisitor;
151
152struct Key<'de>(Cow<'de, str>);
155
156impl<'de> serde::Deserialize<'de> for Key<'de> {
157 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
158 where
159 D: Deserializer<'de>,
160 {
161 deserializer.deserialize_str(KeyVisitor)
162 }
163}
164
165struct KeyVisitor;
166
167impl<'de> Visitor<'de> for KeyVisitor {
168 type Value = Key<'de>;
169
170 fn expecting(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
171 f.write_str("an object key")
172 }
173
174 fn visit_borrowed_str<E: de::Error>(self, v: &'de str) -> Result<Self::Value, E> {
175 Ok(Key(Cow::Borrowed(v)))
176 }
177
178 fn visit_str<E: de::Error>(self, v: &str) -> Result<Self::Value, E> {
181 Ok(Key(Cow::Owned(v.to_owned())))
182 }
183}
184
185impl<'de> Visitor<'de> for DupVisitor {
186 type Value = DupGuard;
187
188 fn expecting(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
189 f.write_str("any JSON value with unique object keys")
190 }
191
192 fn visit_map<A>(self, mut map: A) -> Result<Self::Value, A::Error>
193 where
194 A: MapAccess<'de>,
195 {
196 let mut seen: HashSet<Cow<'de, str>> = HashSet::new();
197 while let Some(Key(key)) = map.next_key::<Key<'de>>()? {
198 if let Some(dup) = seen.replace(key) {
199 return Err(de::Error::custom(format!("duplicate object key `{dup}`")));
200 }
201 map.next_value::<DupGuard>()?;
203 }
204 Ok(DupGuard)
205 }
206
207 fn visit_seq<A>(self, mut seq: A) -> Result<Self::Value, A::Error>
208 where
209 A: SeqAccess<'de>,
210 {
211 while seq.next_element::<DupGuard>()?.is_some() {}
212 Ok(DupGuard)
213 }
214
215 fn visit_bool<E>(self, _v: bool) -> Result<Self::Value, E> {
217 Ok(DupGuard)
218 }
219 fn visit_i64<E>(self, _v: i64) -> Result<Self::Value, E> {
220 Ok(DupGuard)
221 }
222 fn visit_u64<E>(self, _v: u64) -> Result<Self::Value, E> {
223 Ok(DupGuard)
224 }
225 fn visit_f64<E>(self, _v: f64) -> Result<Self::Value, E> {
226 Ok(DupGuard)
227 }
228 fn visit_str<E>(self, _v: &str) -> Result<Self::Value, E> {
229 Ok(DupGuard)
230 }
231 fn visit_none<E>(self) -> Result<Self::Value, E> {
232 Ok(DupGuard)
233 }
234 fn visit_unit<E>(self) -> Result<Self::Value, E> {
235 Ok(DupGuard)
236 }
237 fn visit_some<D>(self, deserializer: D) -> Result<Self::Value, D::Error>
238 where
239 D: Deserializer<'de>,
240 {
241 deserializer.deserialize_any(DupVisitor)
242 }
243}
244
245#[cfg(test)]
246mod tests {
247 use super::{Key, check_no_duplicate_keys};
248 use serde::Deserialize;
249 use serde::de::{IgnoredAny, MapAccess, Visitor};
250 use std::borrow::Cow;
251 use std::fmt;
252
253 struct ObjectKeys<'de>(Vec<Cow<'de, str>>);
254
255 impl<'de> Deserialize<'de> for ObjectKeys<'de> {
256 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
257 where
258 D: serde::Deserializer<'de>,
259 {
260 deserializer.deserialize_map(ObjectKeysVisitor)
261 }
262 }
263
264 struct ObjectKeysVisitor;
265
266 impl<'de> Visitor<'de> for ObjectKeysVisitor {
267 type Value = ObjectKeys<'de>;
268
269 fn expecting(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
270 f.write_str("a JSON object")
271 }
272
273 fn visit_map<A>(self, mut map: A) -> Result<Self::Value, A::Error>
274 where
275 A: MapAccess<'de>,
276 {
277 let mut keys = Vec::new();
278 while let Some(Key(key)) = map.next_key::<Key<'de>>()? {
279 map.next_value::<IgnoredAny>()?;
280 keys.push(key);
281 }
282 Ok(ObjectKeys(keys))
283 }
284 }
285
286 #[test]
287 fn an_unescaped_key_borrows_from_the_payload() {
288 let ObjectKeys(keys) = serde_json::from_slice(br#"{"abc":1,"\u0061bc":2}"#).unwrap();
289 assert!(matches!(keys[0], Cow::Borrowed("abc")));
290 assert!(matches!(keys[1], Cow::Owned(_)));
291 }
292
293 #[test]
294 fn duplicate_key_names_the_key() {
295 let err = check_no_duplicate_keys(br#"{"id":1,"id":2}"#).unwrap_err();
296 assert!(err.is_data, "{err}");
297 assert!(
298 err.to_string().starts_with("duplicate object key `id`"),
299 "{err}"
300 );
301 }
302
303 #[test]
304 fn escaped_spelling_is_the_same_key() {
305 let err = check_no_duplicate_keys(br#"{"\u0061":1,"a":2}"#).unwrap_err();
306 assert!(err.is_data, "{err}");
307 assert!(
308 err.to_string().starts_with("duplicate object key `a`"),
309 "{err}"
310 );
311 }
312
313 #[test]
317 fn plain_spelling_matches_an_escaped_duplicate() {
318 let err = check_no_duplicate_keys(br#"{"a":1,"\u0061":2}"#).unwrap_err();
319 assert!(err.is_data, "{err}");
320 assert!(
321 err.to_string().starts_with("duplicate object key `a`"),
322 "{err}"
323 );
324 }
325
326 #[test]
327 fn same_key_in_sibling_scopes_is_clean() {
328 check_no_duplicate_keys(br#"{"a":{"a":1},"b":[{"a":1},{"a":2}]}"#).unwrap();
329 }
330}