1 use std::error::Error;
2
3 use crate::map::Map;
4 use crate::value::{Value, ValueKind};
5
parse( uri: Option<&String>, text: &str, ) -> Result<Map<String, Value>, Box<dyn Error + Send + Sync>>6 pub fn parse(
7 uri: Option<&String>,
8 text: &str,
9 ) -> Result<Map<String, Value>, Box<dyn Error + Send + Sync>> {
10 // Parse a JSON object value from the text
11 // TODO: Have a proper error fire if the root of a file is ever not a Table
12 let value = from_json_value(uri, &serde_json::from_str(text)?);
13 match value.kind {
14 ValueKind::Table(map) => Ok(map),
15
16 _ => Ok(Map::new()),
17 }
18 }
19
from_json_value(uri: Option<&String>, value: &serde_json::Value) -> Value20 fn from_json_value(uri: Option<&String>, value: &serde_json::Value) -> Value {
21 match *value {
22 serde_json::Value::String(ref value) => Value::new(uri, ValueKind::String(value.clone())),
23
24 serde_json::Value::Number(ref value) => {
25 if let Some(value) = value.as_i64() {
26 Value::new(uri, ValueKind::I64(value))
27 } else if let Some(value) = value.as_f64() {
28 Value::new(uri, ValueKind::Float(value))
29 } else {
30 unreachable!();
31 }
32 }
33
34 serde_json::Value::Bool(value) => Value::new(uri, ValueKind::Boolean(value)),
35
36 serde_json::Value::Object(ref table) => {
37 let mut m = Map::new();
38
39 for (key, value) in table {
40 m.insert(key.clone(), from_json_value(uri, value));
41 }
42
43 Value::new(uri, ValueKind::Table(m))
44 }
45
46 serde_json::Value::Array(ref array) => {
47 let mut l = Vec::new();
48
49 for value in array {
50 l.push(from_json_value(uri, value));
51 }
52
53 Value::new(uri, ValueKind::Array(l))
54 }
55
56 serde_json::Value::Null => Value::new(uri, ValueKind::Nil),
57 }
58 }
59