Serializer implemented; using thiserror for CoronaError

This commit is contained in:
Cerber Ursi
2021-11-27 19:09:08 +07:00
parent f296212d15
commit d69f08cf02
4 changed files with 311 additions and 126 deletions
+5 -1
View File
@@ -7,4 +7,8 @@ edition = "2018"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies] [dependencies]
serde = "1.0" serde = "1.0"
thiserror = "1.0"
[dev_dependencies]
batch_run = "1.0"
+3 -1
View File
@@ -24,4 +24,6 @@ let value = {
``` ```
or the similar construction using [`lazy_static`](http://crates.io/crates/lazy_static). or the similar construction using [`lazy_static`](http://crates.io/crates/lazy_static).
2. As a consequence, all the types used by the serialized one must have distinct names (or they'll clash with each other). 2. As a consequence, all the types used by the serialized one must have distinct names (or they'll clash with each other).
3. Deserializer isn't implemented. This is intentional, since this crate isn't really intended for runtime usage. 3. Deserializer isn't implemented. This is intentional, since this crate isn't really intended for runtime usage.
4. This serializer is intended to use with derived implementation. It may return bogus results when used with customized `Serialize`.
5. It is impossible to serialize the struct with private fields outside from the module it is defined in. In fact, to be able to serialize this type at all, you'll have to distribute two copies of your crate, one of which would only export the definition with derived `Serialize` to be used by this crate during the build-time of the second copy. (Isn't this a bit too complex?)
+8 -8
View File
@@ -1,16 +1,16 @@
use serde::ser; use serde::ser;
use thiserror::Error;
#[derive(Debug)] #[derive(Error, Debug)]
pub struct CoronaError(String); pub enum CoronaError {
#[error("IO error while writing code: {0}")]
impl std::fmt::Display for CoronaError { Io(#[from] std::io::Error),
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { todo!() } #[error("Unknown error: {0}")]
Custom(String),
} }
impl std::error::Error for CoronaError {}
impl ser::Error for CoronaError { impl ser::Error for CoronaError {
fn custom<T>(msg:T)->Self where T: std::fmt::Display { fn custom<T>(msg:T)->Self where T: std::fmt::Display {
Self(msg.to_string()) Self::Custom(msg.to_string())
} }
} }
+295 -116
View File
@@ -1,194 +1,373 @@
use crate::error::CoronaError;
use serde::ser; use serde::ser;
use std::io::Write; use std::io::Write;
use crate::error::CoronaError;
pub struct Corona<W: Write>(W); type SerResult = Result<(), CoronaError>;
impl<W: Write> ser::Serializer for Corona<W> { pub struct Corona<W: Write> {
writer: W,
inside: bool,
}
impl<W: Write> Corona<W> {
fn start_sub(&mut self) -> &mut Self {
self.inside = true;
self
}
fn serialize_item(&mut self, item: impl ser::Serialize) -> SerResult {
if self.inside {
write!(self.writer, ",")?;
}
self.inside = true;
item.serialize(self)?;
Ok(())
}
}
impl<W: Write> ser::Serializer for &mut Corona<W> {
type Ok = (); type Ok = ();
type Error = CoronaError; type Error = CoronaError;
type SerializeSeq = Corona<W>;
type SerializeTuple = Corona<W>;
type SerializeTupleStruct = Corona<W>;
type SerializeTupleVariant = Corona<W>;
type SerializeMap = Corona<W>;
type SerializeStruct = Corona<W>;
type SerializeStructVariant = Corona<W>;
fn serialize_bool(self, v: bool) -> Result<Self::Ok, Self::Error> { todo!() } type SerializeSeq = Self;
type SerializeTuple = Self;
fn serialize_i8(self, v: i8) -> Result<Self::Ok, Self::Error> { todo!() } type SerializeTupleStruct = Self;
type SerializeTupleVariant = Self;
fn serialize_i16(self, v: i16) -> Result<Self::Ok, Self::Error> { todo!() } type SerializeMap = Self;
type SerializeStruct = Self;
fn serialize_i32(self, v: i32) -> Result<Self::Ok, Self::Error> { todo!() } type SerializeStructVariant = Self;
fn serialize_i64(self, v: i64) -> Result<Self::Ok, Self::Error> { todo!() } fn serialize_bool(self, v: bool) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
fn serialize_u8(self, v: u8) -> Result<Self::Ok, Self::Error> { todo!() } Ok(())
}
fn serialize_u16(self, v: u16) -> Result<Self::Ok, Self::Error> { todo!() }
fn serialize_i8(self, v: i8) -> SerResult {
fn serialize_u32(self, v: u32) -> Result<Self::Ok, Self::Error> { todo!() } write!(self.writer, "{}", v.to_string())?;
Ok(())
fn serialize_u64(self, v: u64) -> Result<Self::Ok, Self::Error> { todo!() } }
fn serialize_f32(self, v: f32) -> Result<Self::Ok, Self::Error> { todo!() } fn serialize_i16(self, v: i16) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
fn serialize_f64(self, v: f64) -> Result<Self::Ok, Self::Error> { todo!() } Ok(())
}
fn serialize_char(self, v: char) -> Result<Self::Ok, Self::Error> { todo!() }
fn serialize_i32(self, v: i32) -> SerResult {
fn serialize_str(self, v: &str) -> Result<Self::Ok, Self::Error> { todo!() } write!(self.writer, "{}", v.to_string())?;
Ok(())
fn serialize_bytes(self, v: &[u8]) -> Result<Self::Ok, Self::Error> { todo!() } }
fn serialize_none(self) -> Result<Self::Ok, Self::Error> { todo!() } fn serialize_i64(self, v: i64) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
fn serialize_some<T: ?Sized>(self, value: &T) -> Result<Self::Ok, Self::Error> Ok(())
}
fn serialize_i128(self, v: i128) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
Ok(())
}
fn serialize_u8(self, v: u8) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
Ok(())
}
fn serialize_u16(self, v: u16) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
Ok(())
}
fn serialize_u32(self, v: u32) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
Ok(())
}
fn serialize_u64(self, v: u64) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
Ok(())
}
fn serialize_u128(self, v: u128) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
Ok(())
}
fn serialize_f32(self, v: f32) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
Ok(())
}
fn serialize_f64(self, v: f64) -> SerResult {
write!(self.writer, "{}", v.to_string())?;
Ok(())
}
fn serialize_char(self, v: char) -> SerResult {
write!(self.writer, "'{}'", v)?;
Ok(())
}
fn serialize_str(self, v: &str) -> SerResult {
write!(self.writer, "\"{}\"", v)?;
Ok(())
}
fn serialize_bytes(self, v: &[u8]) -> SerResult {
self.collect_seq(v)?;
Ok(())
}
fn serialize_none(self) -> SerResult {
write!(self.writer, "None")?;
Ok(())
}
fn serialize_some<T: ?Sized>(self, value: &T) -> SerResult
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
{
fn serialize_unit(self) -> Result<Self::Ok, Self::Error> { todo!() } write!(self.writer, "Some(")?;
value.serialize(&mut *self)?;
fn serialize_unit_struct(self, name: &'static str) -> Result<Self::Ok, Self::Error> { todo!() } write!(self.writer, ")")?;
Ok(())
}
fn serialize_unit(self) -> SerResult {
write!(self.writer, "()")?;
Ok(())
}
fn serialize_unit_struct(self, name: &'static str) -> SerResult {
write!(self.writer, "{}()", name)?;
Ok(())
}
fn serialize_unit_variant( fn serialize_unit_variant(
self, self,
name: &'static str, name: &'static str,
variant_index: u32, _variant_index: u32,
variant: &'static str, variant: &'static str,
) -> Result<Self::Ok, Self::Error> { todo!() } ) -> SerResult {
write!(self.writer, "{}::{}()", name, variant)?;
fn serialize_newtype_struct<T: ?Sized>( Ok(())
}
fn serialize_newtype_struct<T: ?Sized>(self, name: &'static str, value: &T) -> SerResult
where
T: serde::Serialize,
{
write!(self.writer, "{}(", name)?;
value.serialize(&mut *self)?;
write!(self.writer, ")")?;
Ok(())
}
fn serialize_newtype_variant<T: ?Sized>(
self, self,
name: &'static str, name: &'static str,
value: &T, _variant_index: u32,
) -> Result<Self::Ok, Self::Error>
where
T: serde::Serialize { todo!() }
fn serialize_newtype_variant<T: ?Sized>(
self,
name: &'static str,
variant_index: u32,
variant: &'static str, variant: &'static str,
value: &T, value: &T,
) -> Result<Self::Ok, Self::Error> ) -> SerResult
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
{
fn serialize_seq(self, len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> { todo!() } write!(self.writer, "{}::{}(", name, variant)?;
value.serialize(&mut *self)?;
fn serialize_tuple(self, len: usize) -> Result<Self::SerializeTuple, Self::Error> { todo!() } write!(self.writer, ")")?;
Ok(())
}
fn serialize_seq(self, _len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> {
write!(self.writer, "vec![")?;
Ok(self.start_sub())
}
fn serialize_tuple(self, _len: usize) -> Result<Self::SerializeTuple, Self::Error> {
write!(self.writer, "(")?;
Ok(self.start_sub())
}
fn serialize_tuple_struct( fn serialize_tuple_struct(
self, self,
name: &'static str, name: &'static str,
len: usize, _len: usize,
) -> Result<Self::SerializeTupleStruct, Self::Error> { todo!() } ) -> Result<Self::SerializeTupleStruct, Self::Error> {
write!(self.writer, "{}(", name)?;
Ok(self.start_sub())
}
fn serialize_tuple_variant( fn serialize_tuple_variant(
self, self,
name: &'static str, name: &'static str,
variant_index: u32, _variant_index: u32,
variant: &'static str, variant: &'static str,
len: usize, _len: usize,
) -> Result<Self::SerializeTupleVariant, Self::Error> { todo!() } ) -> Result<Self::SerializeTupleVariant, Self::Error> {
write!(self.writer, "{}::{}", name, variant)?;
fn serialize_map(self, len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> { todo!() } Ok(self.start_sub())
}
fn serialize_map(self, _len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> {
write!(self.writer, "vec![")?;
Ok(self.start_sub())
}
fn serialize_struct( fn serialize_struct(
self, self,
name: &'static str, name: &'static str,
len: usize, _len: usize,
) -> Result<Self::SerializeStruct, Self::Error> { todo!() } ) -> Result<Self::SerializeStruct, Self::Error> {
write!(self.writer, "{} {{", name)?;
Ok(self.start_sub())
}
fn serialize_struct_variant( fn serialize_struct_variant(
self, self,
name: &'static str, name: &'static str,
variant_index: u32, _variant_index: u32,
variant: &'static str, variant: &'static str,
len: usize, _len: usize,
) -> Result<Self::SerializeStructVariant, Self::Error> { todo!() } ) -> Result<Self::SerializeStructVariant, Self::Error> {
write!(self.writer, "{}::{} {{", name, variant)?;
fn collect_str<T: ?Sized>(self, value: &T) -> Result<Self::Ok, Self::Error> Ok(self.start_sub())
where }
T: std::fmt::Display { todo!() }
} }
impl<W: Write> ser::SerializeSeq for Corona<W> { impl<W: Write> ser::SerializeSeq for &mut Corona<W> {
type Ok = (); type Ok = ();
type Error = CoronaError; type Error = CoronaError;
fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error> fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
fn end(self) -> Result<Self::Ok, Self::Error> { todo!() } {
self.serialize_item(value)
}
fn end(self) -> SerResult {
write!(self.writer, "].into_iter().collect()")?;
Ok(())
}
} }
impl<W: Write> ser::SerializeTuple for Corona<W> { impl<W: Write> ser::SerializeTuple for &mut Corona<W> {
type Ok = (); type Ok = ();
type Error = CoronaError; type Error = CoronaError;
fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error> fn serialize_element<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
fn end(self) -> Result<Self::Ok, Self::Error> { todo!() } {
self.serialize_item(value)
}
fn end(self) -> SerResult {
write!(self.writer, ")")?;
Ok(())
}
} }
impl<W: Write> ser::SerializeTupleStruct for Corona<W> { impl<W: Write> ser::SerializeTupleStruct for &mut Corona<W> {
type Ok = (); type Ok = ();
type Error = CoronaError; type Error = CoronaError;
fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error> fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
fn end(self) -> Result<Self::Ok, Self::Error> { todo!() } {
self.serialize_item(value)
}
fn end(self) -> SerResult {
write!(self.writer, ")")?;
Ok(())
}
} }
impl<W: Write> ser::SerializeTupleVariant for Corona<W> { impl<W: Write> ser::SerializeTupleVariant for &mut Corona<W> {
type Ok = (); type Ok = ();
type Error = CoronaError; type Error = CoronaError;
fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error> fn serialize_field<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
fn end(self) -> Result<Self::Ok, Self::Error> { todo!() } {
self.serialize_item(value)
}
fn end(self) -> SerResult {
write!(self.writer, ")")?;
Ok(())
}
} }
impl<W: Write> ser::SerializeMap for Corona<W> { impl<W: Write> ser::SerializeMap for &mut Corona<W> {
type Ok = (); type Ok = ();
type Error = CoronaError; type Error = CoronaError;
fn serialize_key<T: ?Sized>(&mut self, key: &T) -> Result<(), Self::Error> fn serialize_key<T: ?Sized>(&mut self, key: &T) -> Result<(), Self::Error>
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
{
// a little hack for code reuse
self.serialize_item("(")?;
key.serialize(&mut **self)?;
write!(self.writer, ",")?;
Ok(())
}
fn serialize_value<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error> fn serialize_value<T: ?Sized>(&mut self, value: &T) -> Result<(), Self::Error>
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
fn end(self) -> Result<Self::Ok, Self::Error> { todo!() } {
value.serialize(&mut **self)?;
write!(self.writer, ")")?;
Ok(())
}
fn end(self) -> SerResult {
write!(self.writer, "].into_iter().collect()")?;
Ok(())
}
} }
impl<W: Write> ser::SerializeStruct for Corona<W> { impl<W: Write> ser::SerializeStruct for &mut Corona<W> {
type Ok = (); type Ok = ();
type Error = CoronaError; type Error = CoronaError;
fn serialize_field<T: ?Sized>( fn serialize_field<T: ?Sized>(
&mut self, &mut self,
key: &'static str, key: &'static str,
value: &T, value: &T,
) -> Result<(), Self::Error> ) -> Result<(), Self::Error>
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
fn end(self) -> Result<Self::Ok, Self::Error> { todo!() } {
self.serialize_item(format!("{}:", key))?;
value.serialize(&mut **self)?;
Ok(())
}
fn end(self) -> SerResult {
write!(self.writer, "}}")?;
Ok(())
}
} }
impl<W: Write> ser::SerializeStructVariant for Corona<W> { impl<W: Write> ser::SerializeStructVariant for &mut Corona<W> {
type Ok = (); type Ok = ();
type Error = CoronaError; type Error = CoronaError;
fn serialize_field<T: ?Sized>( fn serialize_field<T: ?Sized>(
&mut self, &mut self,
key: &'static str, key: &'static str,
value: &T, value: &T,
) -> Result<(), Self::Error> ) -> Result<(), Self::Error>
where where
T: serde::Serialize { todo!() } T: serde::Serialize,
fn end(self) -> Result<Self::Ok, Self::Error> { todo!() } {
self.serialize_item(format!("{}:", key))?;
} value.serialize(&mut **self)?;
Ok(())
}
fn end(self) -> SerResult {
write!(self.writer, "}}")?;
Ok(())
}
}