From e4c34740bef80716e09fb6d550eb93d13114b898 Mon Sep 17 00:00:00 2001 From: Harald Hoyer Date: Tue, 18 Dec 2018 19:04:02 +0100 Subject: [PATCH] ii --- src/lib.rs | 101 ++++++++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 93 insertions(+), 8 deletions(-) diff --git a/src/lib.rs b/src/lib.rs index 0c0c155..27f435d 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -45,6 +45,26 @@ macro_rules! chain_error_fn { }; } +#[macro_export] +macro_rules! into_boxed_chain_error_fn { + ( $v:expr $(, $more:expr)* ) => { + |e| Box::::from(e).into_chain_error(line!(), file!(), Some(format!($v, $( $more , )* ))) + }; + ( ) => { + |e| Box::::from(e).into_chain_error(line!(), file!(), None) + }; +} + +#[macro_export] +macro_rules! chain { + ( $v:expr $(, $more:expr)* ) => { + |e| Box::::from(e).into_chain_error(line!(), file!(), Some(format!($v, $( $more , )* ))) + }; + ( ) => { + |e| Box::::from(e).into_chain_error(line!(), file!(), None) + }; +} + #[macro_export] macro_rules! into_chain_error_fn { ( $v:expr $(, $more:expr)* ) => { @@ -167,13 +187,7 @@ macro_rules! derive_chain_error { impl ::std::fmt::Debug for $e { fn fmt(&self, f: &mut ::std::fmt::Formatter) -> ::std::fmt::Result { - writeln!( - f, - "\n{}:{}: {}", - self.filename, - self.line, - self.description() - )?; + writeln!(f, "{}:{}: {}", self.filename, self.line, self.description())?; if let Some(e) = self.source() { writeln!(f, "\nCaused by:")?; ::std::fmt::Debug::fmt(&e, f)?; @@ -200,6 +214,22 @@ mod tests { derive_chain_error!(MyError); derive_chain_error!(MyMainError); + impl ChainErrorFrom> for MyMainError { + fn chain_error_from( + e: Box, + line: u32, + filename: &'static str, + description: Option, + ) -> Self { + MyMainError { + line, + filename, + description, + error_cause: Some(e), + } + } + } + fn throw_error() -> Result<(), MyError> { let directory = String::from("ldfhgdfkgjdf"); ::std::fs::remove_dir(&directory).map_err(chain_error_fn!( @@ -212,9 +242,64 @@ mod tests { } #[test] - fn it_works() -> Result<(), MyMainError> { + fn test_chain_error_fn() -> Result<(), MyMainError> { let res = throw_error().map_err(chain_error_fn!(MyMainError, "I has an error.")); + if let Err(my_err) = res { + if let Some(source) = my_err.source() { + assert!(source.is::()); + } + println!("\nRoot cause is {:#?}\n", my_err.root_cause()); + assert!(my_err.root_cause().unwrap().is::<::std::io::Error>()); + assert!(my_err.find_cause::<::std::io::Error>().is_some()); + + if my_err.find_cause::<::std::io::Error>().is_some() { + println!("Has cause io::Error"); + } + if my_err.find_cause::().is_some() { + println!("Has cause MyError"); + } + println!("-----------"); + println!("Display Error:\n{}", my_err); + println!("-----------"); + println!("Debug Error: \n{:#?}", my_err); + println!("-----------"); + }; + //res?; + Ok(()) + } + #[test] + fn test_into_chain_error_fn() -> Result<(), MyMainError> { + let res: Result<(), MyMainError> = throw_error().map_err(into_boxed_chain_error_fn!("I has an error.")); + + if let Err(my_err) = res { + if let Some(source) = my_err.source() { + assert!(source.is::()); + } + println!("\nRoot cause is {:#?}\n", my_err.root_cause()); + assert!(my_err.root_cause().unwrap().is::<::std::io::Error>()); + assert!(my_err.find_cause::<::std::io::Error>().is_some()); + + if my_err.find_cause::<::std::io::Error>().is_some() { + println!("Has cause io::Error"); + } + if my_err.find_cause::().is_some() { + println!("Has cause MyError"); + } + println!("-----------"); + println!("Display Error:\n{}", my_err); + println!("-----------"); + println!("Debug Error: \n{:#?}", my_err); + println!("-----------"); + }; + //res?; + Ok(()) + } + + #[test] + fn test_map_chain_err() -> Result<(), MyMainError> { + let res: Result<(), MyMainError> = throw_error().map_err(chain!()); + if let Err(my_err) = res { if let Some(source) = my_err.source() { assert!(source.is::());