use serde::ser;
use std::fmt::Display;
use std::mem;
use error::*;
use value::{Value, ValueKind};
use Config;
#[derive(Default, Debug)]
pub struct ConfigSerializer {
keys: Vec<(String, Option<usize>)>,
pub output: Config,
}
impl ConfigSerializer {
fn serialize_primitive<T>(&mut self, value: T) -> Result<()>
where
T: Into<Value> + Display,
{
let key = match self.last_key_index_pair() {
Some((key, Some(index))) => format!("{}[{}]", key, index),
Some((key, None)) => key.to_string(),
None => {
return Err(ConfigError::Message(format!(
"key is not found for value {}",
value
)))
}
};
self.output.set(&key, value.into())?;
Ok(())
}
fn last_key_index_pair(&self) -> Option<(&str, Option<usize>)> {
let len = self.keys.len();
if len > 0 {
self.keys
.get(len - 1)
.map(|&(ref key, opt)| (key.as_str(), opt))
} else {
None
}
}
fn inc_last_key_index(&mut self) -> Result<()> {
let len = self.keys.len();
if len > 0 {
self.keys
.get_mut(len - 1)
.map(|pair| pair.1 = pair.1.map(|i| i + 1).or(Some(0)))
.ok_or_else(|| {
ConfigError::Message(format!("last key is not found in {} keys", len))
})
} else {
Err(ConfigError::Message("keys is empty".to_string()))
}
}
fn make_full_key(&self, key: &str) -> String {
let len = self.keys.len();
if len > 0 {
if let Some(&(ref prev_key, index)) = self.keys.get(len - 1) {
return if let Some(index) = index {
format!("{}[{}].{}", prev_key, index, key)
} else {
format!("{}.{}", prev_key, key)
};
}
}
key.to_string()
}
fn push_key(&mut self, key: &str) {
let full_key = self.make_full_key(key);
self.keys.push((full_key, None));
}
fn pop_key(&mut self) -> Option<(String, Option<usize>)> {
self.keys.pop()
}
}
impl<'a> ser::Serializer for &'a mut ConfigSerializer {
type Ok = ();
type Error = ConfigError;
type SerializeSeq = Self;
type SerializeTuple = Self;
type SerializeTupleStruct = Self;
type SerializeTupleVariant = Self;
type SerializeMap = Self;
type SerializeStruct = Self;
type SerializeStructVariant = Self;
fn serialize_bool(self, v: bool) -> Result<Self::Ok> {
self.serialize_primitive(v)
}
fn serialize_i8(self, v: i8) -> Result<Self::Ok> {
self.serialize_i64(v as i64)
}
fn serialize_i16(self, v: i16) -> Result<Self::Ok> {
self.serialize_i64(v as i64)
}
fn serialize_i32(self, v: i32) -> Result<Self::Ok> {
self.serialize_i64(v as i64)
}
fn serialize_i64(self, v: i64) -> Result<Self::Ok> {
self.serialize_primitive(v)
}
fn serialize_u8(self, v: u8) -> Result<Self::Ok> {
self.serialize_u64(v as u64)
}
fn serialize_u16(self, v: u16) -> Result<Self::Ok> {
self.serialize_u64(v as u64)
}
fn serialize_u32(self, v: u32) -> Result<Self::Ok> {
self.serialize_u64(v as u64)
}
fn serialize_u64(self, v: u64) -> Result<Self::Ok> {
if v > (i64::max_value() as u64) {
Err(ConfigError::Message(format!(
"value {} is greater than the max {}",
v,
i64::max_value()
)))
} else {
self.serialize_i64(v as i64)
}
}
fn serialize_f32(self, v: f32) -> Result<Self::Ok> {
self.serialize_f64(v as f64)
}
fn serialize_f64(self, v: f64) -> Result<Self::Ok> {
self.serialize_primitive(v)
}
fn serialize_char(self, v: char) -> Result<Self::Ok> {
self.serialize_primitive(v.to_string())
}
fn serialize_str(self, v: &str) -> Result<Self::Ok> {
self.serialize_primitive(v.to_string())
}
fn serialize_bytes(self, v: &[u8]) -> Result<Self::Ok> {
use serde::ser::SerializeSeq;
let mut seq = self.serialize_seq(Some(v.len()))?;
for byte