ebi_objects 0.3.182

Objects for Ebi - a stochastic process mining utility
Documentation
use anyhow::Context;
use chrono::{DateTime, FixedOffset};
use ebi_arithmetic::Fraction;
use ebi_arithmetic::anyhow::{Result, anyhow};
use serde_json::{Map, Value};

pub fn read_field_bool(json: &Value, field: &str) -> Result<bool> {
    match &json[field] {
        Value::Null => Err(anyhow!("field not found")),
        Value::Bool(b) => Ok(*b),
        Value::Number(_) => Err(anyhow!("field is a number, where boolean expected")),
        Value::String(_) => Err(anyhow!("field is a literal, where number expected")),
        Value::Array(_) => Err(anyhow!("field is a list, where number expected")),
        Value::Object(_) => Err(anyhow!("field is an object, where number expected")),
    }
}

pub fn read_field_index(json: &Value, field: &str) -> Result<usize> {
    match &json[field] {
        Value::Null => return Err(anyhow!("field not found")),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where number expected")),
        Value::Number(n) => {
            if !n.is_u64() {
                return Err(anyhow!("number is not an integer"));
            }
            return Ok(usize::try_from(n.as_u64().unwrap())?);
        }
        Value::String(s) => return Ok(s.parse::<usize>()?),
        Value::Array(_) => return Err(anyhow!("field is a list, where number expected")),
        Value::Object(_) => return Err(anyhow!("field is an object, where number expected")),
    }
}

pub fn read_field_fraction(json: &Value, field: &str) -> Result<Fraction> {
    match &json[field] {
        Value::Null => return Err(anyhow!("field not found")),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where fraction expected")),
        Value::Number(n) => return Ok(n.to_string().parse::<Fraction>()?),
        Value::String(s) => return Ok(s.parse::<Fraction>()?),
        Value::Array(_) => return Err(anyhow!("field is a list, where fraction expected")),
        Value::Object(_) => return Err(anyhow!("field is an object, where fraction expected")),
    }
}

pub fn read_field_list<'a>(json: &'a Value, field: &str) -> Result<&'a Vec<Value>> {
    match &json[field] {
        Value::Null => return Err(anyhow!("field not found")),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where list expected")),
        Value::Number(_) => return Err(anyhow!("field is a number, where list expected")),
        Value::String(_) => return Err(anyhow!("field is a literal, where list expected")),
        Value::Array(arr) => return Ok(&arr),
        Value::Object(_) => return Err(anyhow!("field is an object, where list expected")),
    }
}

pub fn read_field_object<'a>(json: &'a Value, field: &str) -> Result<&'a Map<String, Value>> {
    match &json[field] {
        Value::Null => return Err(anyhow!("field not found")),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where object expected")),
        Value::Number(_) => return Err(anyhow!("field is a number, where object expected")),
        Value::String(_) => return Err(anyhow!("field is a literal, where object expected")),
        Value::Array(_) => return Err(anyhow!("field is an array, where object expected")),
        Value::Object(obj) => Ok(&obj),
    }
}

pub fn read_field_string<'a>(json: &'a Value, field: &str) -> Result<String> {
    match &json[field] {
        Value::Null => return Err(anyhow!("field not found")),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where literal expected")),
        Value::Number(n) => return Ok(n.to_string()),
        Value::String(s) => return Ok(s.to_string()),
        Value::Array(_) => return Err(anyhow!("field is a list, where literal expected")),
        Value::Object(_) => return Err(anyhow!("field is an object, where literal expected")),
    }
}

pub fn read_field_index_or_null(json: &Value, field: &str) -> Result<Option<usize>> {
    match &json[field] {
        Value::Null => return Ok(None),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where number expected")),
        Value::Number(n) => {
            if !n.is_u64() {
                return Err(anyhow!("number is not an integer"));
            }
            return Ok(Some(usize::try_from(n.as_u64().unwrap())?));
        }
        Value::String(s) => return Ok(Some(s.parse::<usize>()?)),
        Value::Array(_) => return Err(anyhow!("field is a list, where number expected")),
        Value::Object(_) => return Err(anyhow!("field is an object, where number expected")),
    }
}

pub fn read_field_fraction_or_null(json: &Value, field: &str) -> Result<Option<Fraction>> {
    match &json[field] {
        Value::Null => return Ok(None),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where fraction expected")),
        Value::Number(n) => return Ok(Some(n.to_string().parse::<Fraction>()?)),
        Value::String(s) => return Ok(Some(s.parse::<Fraction>()?)),
        Value::Array(_) => return Err(anyhow!("field is a list, where fraction expected")),
        Value::Object(_) => return Err(anyhow!("field is an object, where fraction expected")),
    }
}

pub fn read_field_string_or_null<'a>(json: &'a Value, field: &str) -> Result<Option<String>> {
    match &json[field] {
        Value::Null => return Ok(None),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where literal expected")),
        Value::Number(n) => return Ok(Some(n.to_string())),
        Value::String(s) => return Ok(Some(s.to_string())),
        Value::Array(_) => return Err(anyhow!("field is a list, where literal expected")),
        Value::Object(_) => return Err(anyhow!("field is an object, where literal expected")),
    }
}

pub fn read_field_time_or_null<'a>(
    json: &'a Value,
    field: &str,
) -> Result<Option<DateTime<FixedOffset>>> {
    match &json[field] {
        Value::Null => return Ok(None),
        Value::Bool(_) => return Err(anyhow!("Field is a boolean, where a time was expected.")),
        Value::Number(_) => return Err(anyhow!("Field is a number, where a time was expected.")),
        Value::String(s) => {
            return Ok(Some(
                s.parse()
                    .with_context(|| anyhow!("field cannot be parsed as a time."))?,
            ));
        }
        Value::Array(_) => return Err(anyhow!("Field is a list, where a time was expected.")),
        Value::Object(_) => return Err(anyhow!("Field is an object, where a time was expected.")),
    }
}

pub fn read_index(json: &Value) -> Result<usize> {
    match &json {
        Value::Null => return Err(anyhow!("field not found")),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where number expected")),
        Value::Number(n) => {
            if !n.is_u64() {
                return Err(anyhow!("number is not an integer"));
            }
            return Ok(usize::try_from(n.as_u64().unwrap())?);
        }
        Value::String(_) => return Err(anyhow!("field is a literal, where number expected")),
        Value::Array(_) => return Err(anyhow!("field is a list, where number expected")),
        Value::Object(_) => return Err(anyhow!("field is an object, where number expected")),
    }
}

pub fn read_string(json: &Value) -> Result<&String> {
    match &json {
        Value::Null => return Err(anyhow!("field not found")),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where literal expected")),
        Value::Number(_) => return Err(anyhow!("field is a number, where literal expected")),
        Value::String(s) => return Ok(s),
        Value::Array(_) => return Err(anyhow!("field is a list, where literal expected")),
        Value::Object(_) => return Err(anyhow!("field is an object, where literal expected")),
    }
}

pub fn read_list(json: &Value) -> Result<&Vec<Value>> {
    match &json {
        Value::Null => return Err(anyhow!("field not found")),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where list expected")),
        Value::Number(_) => return Err(anyhow!("field is a number, where list expected")),
        Value::String(_) => return Err(anyhow!("field is a literal, where list expected")),
        Value::Array(s) => return Ok(s),
        Value::Object(_) => return Err(anyhow!("field is an object, where literal expected")),
    }
}

pub fn read_fraction(json: &Value) -> Result<Fraction> {
    match &json {
        Value::Null => return Err(anyhow!("field not found")),
        Value::Bool(_) => return Err(anyhow!("field is a boolean, where fraction expected")),
        Value::Number(n) => return Ok(n.to_string().parse::<Fraction>()?),
        Value::String(s) => return Ok(s.parse::<Fraction>()?),
        Value::Array(_) => return Err(anyhow!("field is a list, where fraction expected")),
        Value::Object(_) => return Err(anyhow!("field is an object, where fraction expected")),
    }
}