use serde::de::DeserializeOwned;
use serde_json::Value;
use std::{borrow::Cow, collections::HashMap};
use crate::error::json_object_error::JsonObjectError;
#[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
pub struct JsonObject {
raw_value: HashMap<Cow<'static, str>, Value>,
is_order: bool,
}
impl JsonObject {
pub fn new(is_order: bool) -> Self {
Self {
raw_value: HashMap::with_capacity(12),
is_order,
}
}
pub fn parse_object<T: DeserializeOwned>(json_str: &str) -> Result<T, JsonObjectError> {
serde_json::from_str::<T>(json_str).map_err(|_| JsonObjectError::PaseError)
}
fn check_key(&self, key: &str) -> bool {
if key.is_empty() {
return false;
}
true
}
}
impl JsonObject {
fn size(&self) -> usize {
self.raw_value.len()
}
fn is_empty(&self) -> bool {
self.raw_value.is_empty()
}
fn contains_key(&self, key: &str) -> bool {
self.raw_value.contains_key(key)
}
fn get<V: DeserializeOwned>(&self, key: &str) -> Option<V> {
self.raw_value
.get(key)
.and_then(|v| serde_json::from_value(v.clone()).ok())
}
fn get_or_default<V: DeserializeOwned>(&self, key: &str, default: V) -> V {
if let Some(v) = self.raw_value.get(key) {
return serde_json::from_value(v.clone()).unwrap_or(default);
}
default
}
fn get_double(&self, key: &str) -> Option<f64> {
self.raw_value.get(key).and_then(|v| v.as_f64())
}
fn get_int(&self, key: &str) -> Option<i64> {
self.raw_value.get(key).and_then(|v| v.as_i64())
}
fn get_uint(&self, key: &str) -> Option<u64> {
self.raw_value.get(key).and_then(|v| v.as_u64())
}
fn get_str(&self, key: &str) -> Option<&str> {
self.raw_value.get(key).and_then(|v| v.as_str())
}
fn get_bool(&self, key: &str) -> Option<bool> {
self.raw_value.get(key).and_then(|v| v.as_bool())
}
fn get_json_array<V: DeserializeOwned>(&self, key: &str) -> Vec<V> {
self.raw_value
.get(key)
.and_then(|v| v.as_array())
.map(|arr| {
arr.iter()
.map(|v| serde_json::from_value(v.clone()).unwrap())
.collect()
})
.unwrap_or_default()
}
fn set<V: Into<Value>>(mut self, key: impl Into<Cow<'static, str>>, value: V) -> Self {
self.raw_value.insert(key.into(), value.into());
return self;
}
fn set_opt<V: Into<Value>>(&mut self, key: impl Into<Cow<'static, str>>, value: V) -> Option<Value> {
self.raw_value.insert(key.into(), value.into())
}
fn put_once<V: Into<Value>>(
&mut self,
key: impl Into<Cow<'static, str>>,
value: V,
) -> Result<(), JsonObjectError> {
let key = key.into();
if !self.check_key(&key) {
return Err(JsonObjectError::KeyIsEmpty);
}
if self.raw_value.contains_key(&key) {
return Err(JsonObjectError::KeyAlreadyExists);
}
self.set_opt(key, value);
Ok(())
}
fn put_opt<V: Into<Value>>(
&mut self,
key: impl Into<String>,
value: V,
) -> Result<(), JsonObjectError> {
let key = key.into();
let value = value.into();
if !self.check_key(&key) {
return Err(JsonObjectError::KeyIsEmpty);
}
if value.is_null() {
return Err(JsonObjectError::KeyOrValueIsNull);
}
self.set_opt(key, value);
Ok(())
}
fn put_all(&mut self, data: impl IntoIterator<Item = (Cow<'static, str>, Value)>) {
self.raw_value.extend(data);
}
fn raw_value(&self) -> &HashMap<Cow<'static, str>, Value> {
&self.raw_value
}
fn clear(&mut self) {
self.raw_value.clear()
}
fn values(&self) -> Vec<&Value> {
self.raw_value.values().collect()
}
fn keys(&self) -> Vec<&Cow<'static, str>> {
self.raw_value.keys().collect()
}
fn to_json_string(&self) -> String {
serde_json::to_string(&self.raw_value).unwrap_or_default()
}
fn to_json_string_pretty(&self) -> String {
serde_json::to_string_pretty(&self.raw_value).unwrap_or_default()
}
}
impl Default for JsonObject {
fn default() -> Self {
Self {
raw_value: HashMap::with_capacity(12),
is_order: false,
}
}
}