Browse Source

start rework design

master
Avril 5 months ago
parent
commit
f884590641
Signed by: flanchan GPG Key ID: 284488987C31F630
  1. 1
      Cargo.toml
  2. 3
      src/ext.rs
  3. 55
      src/formats.rs
  4. 4
      src/lib.rs
  5. 29
      src/object.rs
  6. 89
      src/processor.rs

1
Cargo.toml

@ -20,3 +20,4 @@ serde = {version = "1.0.126", features = ["derive"]}
serde-lexpr = "0.1.2"
serde_cbor = "0.11.1"
serde_json = "1.0.64"
smallbox = "0.8.0"

3
src/ext.rs

@ -0,0 +1,3 @@
use super::*;
pub use object::ObjectExt;

55
src/formats.rs

@ -1,41 +1,32 @@
//! The available formats to convert
use super::*;
use processor::Processor;
use std::io;
use object::{
Object, OwnedObject,
};
/// All formats and their associated processor
pub enum Format
pub struct Config;
/// A directive for a format on how to encode and decode objects.
#[derive(Clone, Copy)]
pub struct FormatDirective
{
Json(processor::Json),
SExpr(processor::Sexpr),
CBor(processor::Cbor),
encode: fn (&Config, &mut dyn io::Write, &dyn Object) -> io::Result<usize>,
decode: fn (&Config, &mut dyn io::Read) -> io::Result<(OwnedObject<'static>, usize)>,
}
impl Format
{
/// The processor for this format
pub fn processor(&self) -> &(dyn Processor + 'static)
{
match &self {
Self::Json(a) => a,
Self::SExpr(a) => a,
Self::CBor(a) => a,
}
}
/// The processor for this format
pub fn processor_mut(&mut self) -> &mut (dyn Processor + 'static)
{
match self {
Self::Json(a) => a,
Self::SExpr(a) => a,
Self::CBor(a) => a,
}
}
macro_rules! directive {
($($name:literal),+ => $encode:expr, $decode:expr) => {
(&[$($name),+], FormatDirective {
encode: $encode,
decode: $decode,
})
};
}
/// All format objects and their name(s)
pub static FORMATS: &[(&'static [&'static str], Format)] = &[
(&["json"], Format::Json(processor::Json)),
(&["s-expression", "sexpr"], Format::SExpr(processor::Sexpr)),
(&["cbor"], Format::CBor(processor::Cbor)),
/// All format directives and their name(s)
pub static FORMATS: &[(&'static [&'static str], FormatDirective)] = &[
directive!("json" => |_, _, _| todo!(), |_, _| todo!()),
directive!("s-expression", "sexpr" => |_, _, _| todo!(), |_, _| todo!()),
directive!("cbor" => |_, _, _| todo!(), |_, _| todo!()),
];

4
src/lib.rs

@ -1,7 +1,9 @@
#![allow(dead_code)]
mod processor;
mod ext; use ext::*;
mod object;
mod formats;
#[cfg(test)]

29
src/object.rs

@ -0,0 +1,29 @@
use super::*;
use smallbox::{
SmallBox,
space,
smallbox,
};
type OwnedObjectStackSize = space::S4;
/// An object that can be expose serialise+deserialise methods
pub trait Object{
// TODO
}
/// A polymorphic `Object` that is owned.
pub type OwnedObject<'a> = SmallBox<dyn Object + 'a, OwnedObjectStackSize>;
pub trait ObjectExt<'a>: Sized
{
fn into_owned(self) -> OwnedObject<'a>;
}
impl<'a, T: 'a> ObjectExt<'a> for T
where T: Object
{
#[inline] fn into_owned(self) -> OwnedObject<'a> {
smallbox!(self)
}
}

89
src/processor.rs

@ -1,89 +0,0 @@
//! Processing
use super::*;
use std::io;
use std::{
fmt, error
};
macro_rules! processor {
($name:ident: {$($body:tt)*}) => {
#[derive(Debug)]
pub struct $name;
impl Processor for $name{$($body)*}
};
}
//TODO: Move this to `object.rs`. Have a type that polymorphises any `Serialize` object, somehow...
//This may be impossible. If it is. Nuke this file, and re-do the `FORMATS` table's value type to `fn(...SOMETHING...) -> io::Result<...SOMETHING...>`
pub type Object = ();
pub trait Processor
{
//TODO: How to design this trait??? eh...
fn read_object(&self, input: &mut dyn io::Read) -> Result<Object, Error>;
fn write_object(&self, obj: &Object, output: &mut dyn io::Write) -> Result<usize, Error>;
}
processor!(Json: {
});
processor!(Sexpr: {
});
processor!(Cbor: {
});
#[derive(Debug)]
enum ErrorKind
{
IO(io::Error),
Unknown,
}
/// Processing error
pub struct Error(ErrorKind, Option<Box<dyn fmt::Display + 'static>>);
impl fmt::Debug for Error
{
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result
{
f.debug_struct("Error")
.field("kind", &self.0)
.field("message_obj", &format_args!("{:?}", self.1.as_ref().map(|x| x.as_ref() as *const _)))
.finish()
}
}
impl From<io::Error> for Error
{
#[inline] fn from(from: io::Error) -> Self
{
Self(ErrorKind::IO(from), None)
}
}
impl error::Error for Error
{
fn source(&self) -> Option<&(dyn error::Error + 'static)> {
Some(match &self.0 {
ErrorKind::IO(io) => io,
_ => return None,
})
}
}
impl fmt::Display for Error
{
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result
{
write!(f, "format processing error")?;
if let Some(msg) = self.1.as_ref() {
write!(f, ": {}", msg)
} else {
Ok(())
}
}
}
Loading…
Cancel
Save