Diffstat (limited to 'src/build.rs')
| -rw-r--r-- | src/build.rs | 120 |
1 files changed, 20 insertions, 100 deletions
diff --git a/src/build.rs b/src/build.rs index 7ac87fd..3723392 100644 --- a/src/build.rs +++ b/src/build.rs @@ -1,15 +1,24 @@ pub mod builders; use crate::{ - effect::{AsObj as _, Effect, EffectAnyTrait, SyncEffect, Yield}, + effect::{Effect, Future}, protocol::Visitor, - Walker, }; /// A buildable type. -pub trait Build<'ctx, E: EffectAnyTrait<'ctx>>: Sized { +pub trait Build<'ctx>: BuilderTypes<'ctx, Value = Self> + Send { /// The builder that can be used to build a value of `Self`. - type Builder: Builder<'ctx, E, Value = Self>; + type Builder<E: Effect<'ctx>>: Builder<'ctx, Seed = Self::Seed, Error = Self::Error, Value = Self, Effect = E>; +} + +pub trait BuilderTypes<'ctx> { + type Seed: Send; + + /// Error that can happen during filling the builder with data. + type Error: Send; + + /// Type to be built. + type Value: Send; } /// Builder for a type. @@ -25,112 +34,23 @@ pub trait Build<'ctx, E: EffectAnyTrait<'ctx>>: Sized { /// the builder with data from it's walk. /// - Call [`Self::build()`] to finish building the value and get any errors /// that happened during filling it with data. -pub trait Builder<'ctx, E: EffectAnyTrait<'ctx>>: AsVisitor<'ctx, E> { - type Effect: Effect<'ctx, Result<Self::Value, Self::Error>>; +pub trait Builder<'ctx>: BuilderTypes<'ctx> + Sized + Send { + type Effect: Effect<'ctx>; - type Seed; - - /// Error that can happen during filling the builder with data. - type Error; - - /// Type to be built. - type Value; - - fn from_seed(seed: Self::Seed) -> Self; + fn from_seed<'a>(seed: Self::Seed) -> Future<'a, 'ctx, Self, Self::Effect> + where + Self: 'a; /// Finish the value. /// /// If an error happened with the builder during the walk /// it will be reported here. - fn build<'a>(self) -> Yield<'a, 'ctx, Result<Self::Value, Self::Error>, Self::Effect> + fn build<'a>(self) -> Future<'a, 'ctx, Result<Self::Value, Self::Error>, Self::Effect> where Self: 'a; -} -pub trait AsVisitor<'ctx, E: EffectAnyTrait<'ctx>> { /// Get the builder as a visitor that a walker can use. /// /// This is expected to just be `self`. - fn as_visitor(&mut self) -> Visitor<'_, 'ctx, E>; + fn as_visitor(&mut self) -> Visitor<'_, 'ctx>; } - -pub trait DefaultBuilder<'ctx, E: EffectAnyTrait<'ctx>>: Builder<'ctx, E> { - fn default() -> Self; -} - -impl<'ctx, B: Builder<'ctx, E>, E: EffectAnyTrait<'ctx>> DefaultBuilder<'ctx, E> for B -where - B::Seed: Default, -{ - fn default() -> Self { - Self::from_seed(Default::default()) - } -} - -#[derive(Debug)] -pub enum BuildError<B, W> { - Builder(B), - Walker(W), -} - -#[inline] -pub fn build<'ctx, T: Build<'ctx, SyncEffect>, W: Walker<'ctx, Effect = SyncEffect>>( - walker: W, -) -> Result< - T, - BuildError< - <<T as Build<'ctx, SyncEffect>>::Builder as Builder<'ctx, SyncEffect>>::Error, - W::Error, - >, -> -where - <T as Build<'ctx, SyncEffect>>::Builder: Builder<'ctx, SyncEffect, Effect = SyncEffect>, - <<T as Build<'ctx, SyncEffect>>::Builder as Builder<'ctx, SyncEffect>>::Seed: Default, -{ - let mut builder = T::Builder::from_seed(Default::default()); - - if let Err(err) = walker.walk(builder.as_visitor().as_obj_mut()) { - return Err(BuildError::Walker(err)); - } - - builder.build().map_err(BuildError::Builder) -} - -pub fn build_with< - 'ctx, - B: Builder<'ctx, SyncEffect, Effect = SyncEffect>, - W: Walker<'ctx, Effect = SyncEffect>, ->( - walker: W, -) -> Result<B::Value, BuildError<B::Error, W::Error>> -where - <B as Builder<'ctx, SyncEffect>>::Seed: Default, -{ - let mut builder = B::from_seed(Default::default()); - - if let Err(err) = walker.walk(builder.as_visitor().as_obj_mut()) { - return Err(BuildError::Walker(err)); - } - - builder.build().map_err(BuildError::Builder) -} - -// #[cfg(feature = "alloc")] -// use crate::protocol::AsyncEffect; -// -// #[cfg(feature = "alloc")] -// pub async fn async_build_with< -// 'ctx, -// B: DefaultBuilder<'ctx, AsyncEffect>, -// W: for<'a> Walker<'a, 'ctx, Effect = AsyncEffect>, -// >( -// walker: W, -// ) -> Result<B::Value, BuildError<B::Error, W::Error>> { -// let mut builder = B::default(); -// -// if let core::ops::ControlFlow::Break(err) = walker.walk(builder.as_visitor()).await { -// return Err(BuildError::Walker(err)); -// } -// -// builder.build().map_err(BuildError::Builder) -// } |