Fallible from_preserves

This commit is contained in:
Tony Garnock-Jones 2021-06-30 09:52:16 +02:00
parent d69787e5ee
commit f1d403a6a7
7 changed files with 71 additions and 52 deletions

View File

@ -11,7 +11,7 @@ pub mod value;
#[cfg(test)]
mod dom {
use super::value::{
Value, IOValue, NestedValue, PlainValue, Domain,
Value, IOValue, IOResult, NestedValue, PlainValue, Domain,
PackedWriter,
};
@ -22,7 +22,7 @@ mod dom {
}
impl Domain for Dom {
fn from_preserves(v: IOValue) -> Self {
fn from_preserves(v: IOValue) -> IOResult<Self> {
panic!("Cannot decode IOValue to Dom: {:?}", v);
}

View File

@ -33,6 +33,8 @@ pub use repr::FALSE;
pub use repr::TRUE;
pub use repr::EMPTY_SEQ;
pub type IOResult<T> = std::result::Result<T, std::io::Error>;
pub fn invert_map<A, B>(m: &Map<A, B>) -> Map<B, A>
where A: Clone, B: Clone + Ord
{

View File

@ -5,8 +5,7 @@ pub mod writer;
pub use reader::PackedReader;
pub use writer::PackedWriter;
use super::{Reader, IOValue};
use super::reader::IOResult;
use super::{Reader, IOValue, IOResult};
pub fn from_bytes(bs: &[u8]) -> IOResult<IOValue> {
PackedReader::decode_bytes(bs).demand_next(false)

View File

@ -4,18 +4,29 @@ use std::borrow::Cow;
use std::convert::TryFrom;
use std::convert::TryInto;
use std::marker::PhantomData;
use super::super::signed_integer::SignedInteger;
use super::super::repr::{Value, NestedValue, Domain, IOValue, FALSE, TRUE, Map, Set, Record, Annotations};
use super::constants::Tag;
use super::super::reader::{
BinarySource,
BytesBinarySource,
ConfiguredReader,
IOBinarySource,
use super::super::{
FALSE,
IOResult,
Reader,
ReaderResult,
IOValue,
Map,
NestedValue,
Record,
Set,
TRUE,
Value,
reader::{
BinarySource,
BytesBinarySource,
ConfiguredReader,
IOBinarySource,
Reader,
ReaderResult,
},
repr::Annotations,
signed_integer::SignedInteger,
};
use crate::error::{self, ExpectedKind, Received, is_eof_io_error, io_syntax_error};
@ -264,7 +275,7 @@ impl<'de, S: BinarySource<'de>> Reader<'de> for PackedReader<'de, S> {
}
Tag::Embedded => {
let v = self.demand_next(read_annotations)?;
Value::Domain(IOValue::from_preserves(v)).wrap()
Value::Domain(v).wrap()
}
Tag::SmallInteger(v) => {
// TODO: prebuild these in value.rs

View File

@ -1,10 +1,10 @@
use std::borrow::Cow;
use std::io::{Read, Error};
use std::io::Read;
use std::marker::PhantomData;
use super::repr::{NestedValue, IOValue};
use super::IOResult;
use crate::error::{self, ExpectedKind, Received, io_eof};
pub type IOResult<T> = std::result::Result<T, Error>;
pub type ReaderResult<T> = std::result::Result<T, error::Error>;
pub trait Reader<'de> {

View File

@ -16,11 +16,12 @@ use std::vec::Vec;
pub use std::collections::BTreeSet as Set;
pub use std::collections::BTreeMap as Map;
use super::IOResult;
use super::signed_integer::SignedInteger;
use crate::error::{Error, ExpectedKind, Received};
pub trait Domain: Sized + Debug + Clone + Eq + Hash + Ord {
fn from_preserves(v: IOValue) -> Self;
fn from_preserves(v: IOValue) -> IOResult<Self>;
fn as_preserves(&self) -> IOValue;
}
@ -39,19 +40,19 @@ pub trait NestedValue<D: Domain>: Sized + Debug + Clone + Eq + Hash + Ord {
self.value().fmt(f)
}
fn copy_via<M: NestedValue<E>, E: Domain, F>(&self, f: &F) -> M
fn copy_via<M: NestedValue<E>, E: Domain, F>(&self, f: &F) -> IOResult<M>
where
F: Fn(&D) -> Value<M, E>
F: Fn(&D) -> IOResult<Value<M, E>>
{
M::wrap(self.annotations().copy_via(f), self.value().copy_via(f))
Ok(M::wrap(self.annotations().copy_via(f)?, self.value().copy_via(f)?))
}
fn to_io_value(&self) -> IOValue {
self.copy_via(&|d| d.as_preserves().value().clone())
self.copy_via(&|d| Ok(d.as_preserves().value().clone())).unwrap()
}
fn from_io_value(v: &IOValue) -> Self {
v.copy_via(&|d| Value::Domain(D::from_preserves(d.clone())))
fn from_io_value(v: &IOValue) -> IOResult<Self> {
v.copy_via(&|d| Ok(Value::Domain(D::from_preserves(d.clone())?)))
}
}
@ -739,11 +740,11 @@ impl<N: NestedValue<D>, D: Domain> Value<N, D> {
self.as_embedded().ok_or_else(|| self.expected(ExpectedKind::Embedded))
}
pub fn copy_via<M: NestedValue<E>, E: Domain, F>(&self, f: &F) -> Value<M, E>
pub fn copy_via<M: NestedValue<E>, E: Domain, F>(&self, f: &F) -> IOResult<Value<M, E>>
where
F: Fn(&D) -> Value<M, E>
F: Fn(&D) -> IOResult<Value<M, E>>
{
match self {
Ok(match self {
Value::Boolean(b) => Value::Boolean(*b),
Value::Float(f) => Value::Float(f.clone()),
Value::Double(d) => Value::Double(d.clone()),
@ -752,13 +753,17 @@ impl<N: NestedValue<D>, D: Domain> Value<N, D> {
Value::ByteString(ref v) => Value::ByteString(v.clone()),
Value::Symbol(ref v) => Value::Symbol(v.clone()),
Value::Record(ref r) =>
Value::Record(Record(r.fields_vec().iter().map(|a| a.copy_via(f)).collect())),
Value::Sequence(ref v) => Value::Sequence(v.iter().map(|a| a.copy_via(f)).collect()),
Value::Set(ref v) => Value::Set(v.iter().map(|a| a.copy_via(f)).collect()),
Value::Record(Record(r.fields_vec().iter().map(|a| a.copy_via(f))
.collect::<Result<Vec<_>, _>>()?)),
Value::Sequence(ref v) => Value::Sequence(v.iter().map(|a| a.copy_via(f))
.collect::<IOResult<Vec<_>>>()?),
Value::Set(ref v) => Value::Set(v.iter().map(|a| a.copy_via(f))
.collect::<IOResult<Set<_>>>()?),
Value::Dictionary(ref v) =>
Value::Dictionary(v.iter().map(|(a,b)| (a.copy_via(f), b.copy_via(f))).collect()),
Value::Domain(d) => f(d),
}
Value::Dictionary(v.iter().map(|(a,b)| Ok((a.copy_via(f)?, b.copy_via(f)?)))
.collect::<IOResult<Map<_, _>>>()?),
Value::Domain(d) => f(d)?,
})
}
}
@ -808,7 +813,8 @@ pub fn serialize_nested_value<S, N, D: Domain>(v: &N, serializer: S) ->
pub fn deserialize_nested_value<'de, D, N, Dom: Domain>(deserializer: D) ->
Result<N, D::Error> where D: serde::Deserializer<'de>, N: NestedValue<Dom> + serde::Deserialize<'de>
{
Ok(N::from_io_value(&super::magic::input_value(deserializer)?))
N::from_io_value(&super::magic::input_value(deserializer)?)
.map_err(|e| serde::de::Error::custom(format!("{:?}", e)))
}
//---------------------------------------------------------------------------
@ -847,16 +853,17 @@ impl<N: NestedValue<D>, D: Domain> Annotations<N, D> {
self
}
pub fn copy_via<M: NestedValue<E>, E: Domain, F>(&self, f: &F) -> Annotations<M, E>
pub fn copy_via<M: NestedValue<E>, E: Domain, F>(&self, f: &F) -> IOResult<Annotations<M, E>>
where
F: Fn(&D) -> Value<M, E>
F: Fn(&D) -> IOResult<Value<M, E>>
{
match self.0 {
Ok(match self.0 {
None =>
Annotations(None, PhantomData),
Some(ref b) =>
Annotations(Some(b.iter().map(|a| a.copy_via(f)).collect()), PhantomData),
}
Annotations(Some(b.iter().map(|a| a.copy_via(f)).collect::<Result<Vec<_>, _>>()?),
PhantomData),
})
}
}
@ -1060,8 +1067,8 @@ pub struct IOValue(Arc<AnnotatedValue<IOValue, IOValue>>);
pub type UnwrappedIOValue = Value<IOValue, IOValue>;
impl Domain for IOValue {
fn from_preserves(v: IOValue) -> Self {
v
fn from_preserves(v: IOValue) -> IOResult<Self> {
Ok(v)
}
fn as_preserves(&self) -> IOValue {
@ -1106,8 +1113,8 @@ impl NestedValue<IOValue> for IOValue {
self.clone()
}
fn from_io_value(v: &IOValue) -> Self {
v.clone()
fn from_io_value(v: &IOValue) -> IOResult<Self> {
Ok(v.clone())
}
}

View File

@ -1,7 +1,7 @@
use num::bigint::BigInt;
use std::io::Error;
use super::signed_integer::SignedIntegerRepr;
use super::repr::{Domain, Value, NestedValue, IOValue, UnwrappedIOValue, Float, Double};
use super::repr::{Value, NestedValue, IOValue, UnwrappedIOValue, Float, Double};
pub type Result<T> = std::result::Result<T, Error>;
@ -87,11 +87,11 @@ pub trait Writer: Sized {
Value::SignedInteger(n) => match n.repr() {
SignedIntegerRepr::I128(i) => self.write_i128(*i),
SignedIntegerRepr::U128(u) => self.write_u128(*u),
SignedIntegerRepr::Big(ref n) => self.write_int(n),
SignedIntegerRepr::Big(n) => self.write_int(n),
}
Value::String(ref s) => self.write_string(s),
Value::ByteString(ref bs) => self.write_bytes(bs),
Value::Symbol(ref s) => self.write_symbol(s),
Value::String(s) => self.write_string(s),
Value::ByteString(bs) => self.write_bytes(bs),
Value::Symbol(s) => self.write_symbol(s),
Value::Record(r) => {
let mut c = self.start_record(Some(r.arity()))?;
c.extend()?;
@ -104,7 +104,7 @@ pub trait Writer: Sized {
}
self.end_seq(c)
}
Value::Sequence(ref vs) => {
Value::Sequence(vs) => {
let mut c = self.start_sequence(Some(vs.len()))?;
for v in vs {
c.extend()?;
@ -113,7 +113,7 @@ pub trait Writer: Sized {
}
self.end_seq(c)
}
Value::Set(ref vs) => {
Value::Set(vs) => {
let mut c = self.start_set(Some(vs.len()))?;
for v in vs {
c.extend()?;
@ -122,7 +122,7 @@ pub trait Writer: Sized {
}
self.end_set(c)
}
Value::Dictionary(ref vs) => {
Value::Dictionary(vs) => {
let mut c = self.start_dictionary(Some(vs.len()))?;
for (k, v) in vs {
c.extend()?;
@ -132,9 +132,9 @@ pub trait Writer: Sized {
}
self.end_set(c)
}
Value::Domain(ref d) => {
Value::Domain(d) => {
let mut c = self.start_embedded()?;
c.write(&d.as_preserves())?;
c.write(&d)?;
self.end_embedded(c)
}
}