use effectful::{ blocking::BlockingSpin, bound::{Bool, IsSend, IsSync}, effective::{Canonical, Effective}, environment::Environment, forward_send_sync, }; use mockall::mock; use treaty::{ any::{type_name, AnyTrait}, protocol::{ visitor::{ visit_recoverable, visit_sequence, DynRecoverableScope, DynSequenceScope, Recoverable, RecoverableScope, RequestHint, Sequence, SequenceScope, Value, VisitResult, }, AsVisitor, DynVisitor, DynWalker, }, Flow, Status, }; mock! { pub RecoverableVisitor { pub fn visit<'a, 'ctx>(&mut self, scope: DynRecoverableScope<'a, 'ctx, E>) -> VisitResult; } } forward_send_sync!({} {} {E: (Environment + Send)} MockRecoverableVisitor); // any_trait! { // impl['ctx][E] MockRecoverableVisitor = [ // RecoverableProto // ] where // E: Environment, // } impl<'ctx, E: Environment + Send> Recoverable<'ctx, E> for MockRecoverableVisitor { fn visit<'a>( &'a mut self, scope: DynRecoverableScope<'a, 'ctx, E>, ) -> Canonical<'a, VisitResult, E> { E::value(self.visit(scope)).cast() } } mock! { pub RecoverableScopeVisitor { pub fn new_walk<'r, 'src>(&'r mut self, visitor: DynVisitor<'r, 'src, E>) -> Status; } } forward_send_sync!({} {} {E: (Environment + Send)} MockRecoverableScopeVisitor); impl<'ctx, E: Environment + Send> RecoverableScope<'ctx, E> for MockRecoverableScopeVisitor { fn new_walk<'r>(&'r mut self, visitor: DynVisitor<'r, 'ctx, E>) -> Canonical<'r, Status, E> { E::value(self.new_walk(visitor)).cast() } } pub trait RecoverableVisitorExt<'ctx> { fn visit_recoverable_and_done<'a>( &'a mut self, scope: DynRecoverableScope<'a, 'ctx, BlockingSpin>, ); } impl<'ctx, T> RecoverableVisitorExt<'ctx> for T where T: AsVisitor<'ctx, BlockingSpin>, { fn visit_recoverable_and_done<'a>( &'a mut self, scope: DynRecoverableScope<'a, 'ctx, BlockingSpin>, ) { let result = visit_recoverable(self.as_visitor(), scope).wait(); assert_eq!(result, VisitResult::Control(Flow::Done)); } }