Skip to main content

json_syntax/convert/
serde_json.rs

1use crate::{JsonNumber, JsonNumberBuf, JsonValue};
2
3impl JsonValue {
4	/// Converts a [`serde_json::Value`] into a `Value`.
5	///
6	/// # Example
7	///
8	/// ```
9	/// use json_syntax::JsonValue;
10	///
11	/// // First we create a `serde_json` value.
12	/// let a = serde_json::json!({
13	///   "foo": 1,
14	///   "bar": [2, 3]
15	/// });
16	///
17	/// // We convert the `serde_json` value into a `json_syntax` value.
18	/// let b = JsonValue::from_serde_json(a);
19	///
20	/// // We convert it back into a `serde_json` value.
21	/// let _ = JsonValue::into_serde_json(b);
22	/// ```
23	pub fn from_serde_json(value: serde_json::Value) -> Self {
24		match value {
25			serde_json::Value::Null => Self::Null,
26			serde_json::Value::Bool(b) => Self::Boolean(b),
27			serde_json::Value::Number(n) => Self::Number(n.into()),
28			serde_json::Value::String(s) => Self::String(s.into()),
29			serde_json::Value::Array(a) => {
30				Self::Array(a.into_iter().map(Self::from_serde_json).collect())
31			}
32			serde_json::Value::Object(o) => Self::Object(
33				o.into_iter()
34					.map(|(k, v)| (k.into(), Self::from_serde_json(v)))
35					.collect(),
36			),
37		}
38	}
39
40	/// Converts a `Value` into a [`serde_json::Value`].
41	///
42	/// # Example
43	///
44	/// ```
45	/// use json_syntax::JsonValue;
46	///
47	/// // First we create a `serde_json` value.
48	/// let a = serde_json::json!({
49	///   "foo": 1,
50	///   "bar": [2, 3]
51	/// });
52	///
53	/// // We convert the `serde_json` value into a `json_syntax` value.
54	/// let b = JsonValue::from_serde_json(a);
55	///
56	/// // We convert it back into a `serde_json` value.
57	/// let _ = JsonValue::into_serde_json(b);
58	/// ```
59	pub fn into_serde_json(self) -> serde_json::Value {
60		match self {
61			Self::Null => serde_json::Value::Null,
62			Self::Boolean(b) => serde_json::Value::Bool(b),
63			Self::Number(n) => serde_json::Value::Number(n.into()),
64			Self::String(s) => serde_json::Value::String(s.into_string()),
65			Self::Array(a) => {
66				serde_json::Value::Array(a.into_iter().map(JsonValue::into_serde_json).collect())
67			}
68			Self::Object(o) => serde_json::Value::Object(
69				o.into_iter()
70					.map(|(key, value)| (key.into_string(), JsonValue::into_serde_json(value)))
71					.collect(),
72			),
73		}
74	}
75}
76
77impl From<serde_json::Value> for JsonValue {
78	#[inline(always)]
79	fn from(value: serde_json::Value) -> Self {
80		Self::from_serde_json(value)
81	}
82}
83
84impl From<JsonValue> for serde_json::Value {
85	fn from(value: JsonValue) -> Self {
86		value.into_serde_json()
87	}
88}
89
90impl From<serde_json::Number> for JsonNumberBuf {
91	#[inline(always)]
92	fn from(n: serde_json::Number) -> Self {
93		JsonNumberBuf::new(n.to_string())
94			.ok()
95			.expect("invalid `serde_json::Number`")
96	}
97}
98
99impl From<JsonNumberBuf> for serde_json::Number {
100	#[inline(always)]
101	fn from(n: JsonNumberBuf) -> Self {
102		Self::from(n.as_number())
103	}
104}
105
106impl<'n> From<&'n JsonNumber> for serde_json::Number {
107	fn from(n: &'n JsonNumber) -> Self {
108		if let Some(u) = n.as_u64() {
109			u.into()
110		} else if let Some(i) = n.as_i64() {
111			i.into()
112		} else {
113			match n.as_str().parse() {
114				Ok(n) => n,
115				Err(_) => Self::from_f64(n.as_f64_lossy()).unwrap(),
116			}
117		}
118	}
119}
120
121#[cfg(test)]
122mod tests {
123	use crate::JsonNumberBuf;
124
125	#[test]
126	fn serde_json_arbitrary_number_precision_compatibility() {
127		let n = JsonNumberBuf::new("1.1".to_owned().into_bytes()).unwrap();
128		let serde_json::Value::Number(serde_json_n) = serde_json::to_value(n.clone()).unwrap()
129		else {
130			panic!("not a number")
131		};
132
133		let m: JsonNumberBuf = serde_json_n.into();
134		assert_eq!(n, m)
135	}
136}