SHARE
TWEET

Untitled

a guest Oct 23rd, 2019 74 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. use std::error::Error;
  2. use std::fmt;
  3. use std::str;
  4.  
  5. type DynError = dyn Error + Send + Sync + 'static;
  6.  
  7. #[derive(Debug)]
  8. struct AggErr {
  9.     err: Vec<Box<DynError>>,
  10. }
  11.  
  12. impl AggErr {
  13.     fn push<E: Into<Box<DynError>>>(&mut self, err: E) {
  14.         self.err.push(err.into())
  15.     }
  16. }
  17.  
  18. impl Error for AggErr {}
  19.  
  20. impl fmt::Display for AggErr {
  21.     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
  22.         write!(f, "{} errors:\n", self.err.len())?;
  23.         for e in &self.err {
  24.             write!(f, "  {}\n", e)?;
  25.         }
  26.         Ok(())
  27.     }
  28. }
  29.  
  30. // NOTE: Would probably require `Try` operator support to also allow `Some` and
  31. // `None`.
  32. macro_rules! validated_inner {
  33.     (
  34.         [$($pre:tt)*] [$($post:tt)*] $err:ident =>
  35.         let+ $p:pat = $e:expr; $($rest:tt)*
  36.     ) => {
  37.         validated_inner!(
  38.             [
  39.                 $($pre)*
  40.                 let x = match $e {
  41.                     Ok(x) => Some(x),
  42.                     Err(e) => {
  43.                         $err.push(e);
  44.                         None
  45.                     }
  46.                 };
  47.             ]
  48.             [
  49.                 $($post)*
  50.                 let $p = match x {
  51.                     Some(x) => x,
  52.                     None => break Err($err),
  53.                 };
  54.             ]
  55.             $err => $($rest)*
  56.         )
  57.     };
  58.    
  59.     (
  60.         [$($pre:tt)*] [$($post:tt)*] $err:ident =>
  61.         $e:expr
  62.     ) => {
  63.         loop {
  64.             let mut $err = AggErr { err: Vec::new() };
  65.             $($pre)*
  66.             $($post)*
  67.             break Ok($e);
  68.         }
  69.     };
  70. }
  71.  
  72. macro_rules! validated {
  73.     (let+ $($t:tt)*) => {
  74.         validated_inner!([] [] err => let+ $($t)*)
  75.     }
  76. }
  77.  
  78. fn main() {
  79.     let res: Result<String, AggErr> = validated! {
  80.         let+ x = str::from_utf8(b"yay");
  81.         let+ y = str::from_utf8(b"wo\xffw");
  82.         let+ z = str::from_utf8(b"\xff\xff");
  83.         format!("{}, {}, {}", x, y, z)
  84.     };
  85. }
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
Not a member of Pastebin yet?
Sign Up, it unlocks many cool features!
 
Top