lemma/serialization/
json.rs1use crate::planning::semantics::{DataDefinition, DataPath};
2use crate::Error;
3use indexmap::IndexMap;
4use serde::{Deserialize, Deserializer, Serialize, Serializer};
5use serde_json::Value;
6use std::collections::HashMap;
7
8pub fn from_json(json: &[u8]) -> Result<HashMap<String, Value>, Error> {
14 let map: HashMap<String, Value> = serde_json::from_slice(json)
15 .map_err(|e| Error::validation(format!("JSON parse error: {}", e), None, None::<String>))?;
16
17 Ok(data_values_from_map(map))
18}
19
20pub fn data_values_from_map(map: HashMap<String, Value>) -> HashMap<String, Value> {
22 map.into_iter().filter(|(_, v)| !v.is_null()).collect()
23}
24
25pub fn data_values_from_strings(map: HashMap<String, String>) -> HashMap<String, Value> {
27 map.into_iter()
28 .map(|(k, v)| (k, Value::String(v)))
29 .collect()
30}
31
32pub fn serialize_resolved_data_value_map<S>(
34 map: &IndexMap<DataPath, DataDefinition>,
35 serializer: S,
36) -> Result<S::Ok, S::Error>
37where
38 S: Serializer,
39{
40 let entries: Vec<(&DataPath, &DataDefinition)> = map.iter().collect();
41 entries.serialize(serializer)
42}
43
44pub fn deserialize_resolved_data_value_map<'de, D>(
46 deserializer: D,
47) -> Result<IndexMap<DataPath, DataDefinition>, D::Error>
48where
49 D: Deserializer<'de>,
50{
51 let entries: Vec<(DataPath, DataDefinition)> = Vec::deserialize(deserializer)?;
52 Ok(entries.into_iter().collect())
53}
54
55#[cfg(test)]
56mod tests {
57 use super::*;
58
59 #[test]
60 fn test_json_string_preserved() {
61 let json = br#"{"name": "Alice"}"#;
62 let result = from_json(json).unwrap();
63 assert_eq!(
64 result.get("name"),
65 Some(&Value::String("Alice".to_string()))
66 );
67 }
68
69 #[test]
70 fn test_json_number_preserved_in_map() {
71 let json = br#"{"count": 42}"#;
72 let result = from_json(json).unwrap();
73 assert!(result.get("count").unwrap().is_number());
74 }
75
76 #[test]
77 fn test_null_value_skipped() {
78 let json = br#"{"name": null, "age": "30"}"#;
79 let result = from_json(json).unwrap();
80 assert_eq!(result.len(), 1);
81 assert!(!result.contains_key("name"));
82 assert_eq!(result.get("age"), Some(&Value::String("30".to_string())));
83 }
84
85 #[test]
86 fn test_invalid_json_syntax() {
87 let json = br#"{"name": }"#;
88 let result = from_json(json);
89 assert!(result.is_err());
90 assert!(result.unwrap_err().to_string().contains("JSON parse error"));
91 }
92}