From ed710fada3c1ad0edd525cae512d65065da26ef3 Mon Sep 17 00:00:00 2001 From: Harald Hoyer Date: Tue, 1 Sep 2020 21:03:01 +0200 Subject: [PATCH] rename `cherr()` to `context()` --- Cargo.toml | 4 +- README.md | 23 +++----- booksrc/tutorial1.md | 2 +- booksrc/tutorial10.md | 6 +-- booksrc/tutorial2.md | 15 +++--- booksrc/tutorial3.md | 4 +- booksrc/tutorial4.md | 13 ++--- booksrc/tutorial8.md | 6 +-- examples/example.rs | 10 ++-- examples/tutorial10.rs | 10 ++-- examples/tutorial11.rs | 10 ++-- examples/tutorial12.rs | 10 ++-- examples/tutorial13.rs | 10 ++-- examples/tutorial14.rs | 12 +++-- examples/tutorial15.rs | 14 ++--- examples/tutorial2.rs | 4 +- examples/tutorial3.rs | 5 +- examples/tutorial4.rs | 5 +- examples/tutorial5.rs | 5 +- examples/tutorial6.rs | 5 +- examples/tutorial7.rs | 5 +- examples/tutorial8.rs | 9 ++-- examples/tutorial9.rs | 13 ++--- src/lib.rs | 120 +++++++++++++++-------------------------- tests/test_iter.rs | 48 ++++++++--------- 25 files changed, 169 insertions(+), 199 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index d52a6ad..1341e0c 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -23,7 +23,5 @@ is-it-maintained-issue-resolution = { repository = "haraldh/chainerror" } is-it-maintained-open-issues = { repository = "haraldh/chainerror" } [features] -default = [ "location", "debug-cause" ] -location = [] +default = [] display-cause = [] -debug-cause = [] diff --git a/README.md b/README.md index 6ee78fe..ef73cae 100644 --- a/README.md +++ b/README.md @@ -22,18 +22,9 @@ Debug information is worth it! ### Features -`default = [ "location", "debug-cause" ]` - -`location` -: store the error location - `display-cause` : turn on printing a backtrace of the errors in `Display` -`debug-cause` -: print a backtrace of the errors in `Debug` - - ## Tutorial Read the [Tutorial](https://haraldh.github.io/chainerror/tutorial1.html) @@ -101,12 +92,12 @@ fn do_some_io() -> Result<(), Box> { fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(format!("Error reading '{}'", filename))?; + do_some_io().context(format!("Error reading '{}'", filename))?; Ok(()) } fn func1() -> Result<(), Box> { - func2().cherr("func1 error")?; + func2().context("func1 error")?; Ok(()) } @@ -139,14 +130,14 @@ fn do_some_io() -> Result<(), Box> { fn func3() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(format!("Error reading '{}'", filename))?; + do_some_io().context(format!("Error reading '{}'", filename))?; Ok(()) } -derive_str_cherr!(Func2Error); +derive_str_context!(Func2Error); fn func2() -> ChainResult<(), Func2Error> { - func3().cherr(Func2Error("func2 error: calling func3".into()))?; + func3().context(Func2Error("func2 error: calling func3".into()))?; Ok(()) } @@ -171,9 +162,9 @@ impl ::std::fmt::Debug for Func1Error { } fn func1() -> ChainResult<(), Func1Error> { - func2().cherr(Func1Error::Func2)?; + func2().context(Func1Error::Func2)?; let filename = String::from("bar.txt"); - do_some_io().cherr(Func1Error::IO(filename))?; + do_some_io().context(Func1Error::IO(filename))?; Ok(()) } diff --git a/booksrc/tutorial1.md b/booksrc/tutorial1.md index ae73400..57a502f 100644 --- a/booksrc/tutorial1.md +++ b/booksrc/tutorial1.md @@ -9,7 +9,7 @@ this only prints out the last `Error`. ~~~ -Error: StringError("func1 error") +Error: "func1 error" ~~~ The next chapters of this tutorial show how `chainerror` adds more information diff --git a/booksrc/tutorial10.md b/booksrc/tutorial10.md index e7f2ee4..17c6b63 100644 --- a/booksrc/tutorial10.md +++ b/booksrc/tutorial10.md @@ -5,8 +5,8 @@ To cope with different kind of errors, we introduce the kind of an error `Func1E Because we derive `Debug` and implement `Display` our `Func1ErrorKind` enum, this enum can be used as a `std::error::Error`. -Not using `String` errors anymore, the `cherr!()` macro seen in the beginning of -the tutorial has to be used again. +Not using `String` errors anymore, the `context()` function seen in the beginning of +the tutorial can be used again. Only returning `Func1ErrorKind` in `func1()` now let us get rid of `Result<(), Box>` and we can use `ChainResult<(), Func1ErrorKind>`. @@ -22,4 +22,4 @@ Also a nice `match` on `ChainError.kind()` is now possible, which returns `&T # mod chainerror { {{#rustdoc_include ../src/lib.rs:-1}} # } -~~~ \ No newline at end of file +~~~ diff --git a/booksrc/tutorial2.md b/booksrc/tutorial2.md index e7c5e6d..27e1fbb 100644 --- a/booksrc/tutorial2.md +++ b/booksrc/tutorial2.md @@ -1,7 +1,7 @@ # Simple Chained String Errors -With relatively small changes and the help of the `cherr!` macro of the `chainerror` crate -the `String` errors are now chained together. +With relatively small changes and the help of the `context()` method of the `chainerror` crate +the `&str` errors are now chained together. Press the play button in the upper right corner and see the nice debug output. @@ -19,14 +19,13 @@ Press the play button in the upper right corner and see the nice debug output. {{#include ../examples/tutorial2.rs:13:15}} ~~~ -The macro `cherr!(olderror, newerror)` stores `olderror` as the source/cause of `newerror` -along with the filename (`file!()`) and line number (`line!()`) -and returns `newerror`. +The function `context(newerror)` stores `olderror` as the source/cause of `newerror` +along with the `Location` of the `context()` call and returns `Err(newerror)`. -`Err()?` then returns the inner error applying `.into()`, so that we +`?` then returns the inner error applying `.into()`, so that we again have a `Err(Box)` as a result. -The `Debug` implementation of `ChainError` (which is returned by `cherr!()`) +The `Debug` implementation of `ChainError` (which is returned by `context()`) prints the `Debug` of `T` prefixed with the stored filename and line number. -`ChainError` in our case is `ChainError`. +`ChainError` in our case is `ChainError<&str>`. diff --git a/booksrc/tutorial3.md b/booksrc/tutorial3.md index cc832a9..e44cc7d 100644 --- a/booksrc/tutorial3.md +++ b/booksrc/tutorial3.md @@ -1,6 +1,6 @@ # Mapping Errors -Now let's get more rust idiomatic by using `.map_err()`. +Now let's get more rust idiomatic by using `.context()` directly on the previous `Result`. ~~~rust {{#include ../examples/tutorial3.rs}} @@ -26,4 +26,4 @@ src/main.rs:16: "func1 error" This is, because we caught the error of `func1()` in `main()` and print it out ourselves. We can now control, whether to output in `Debug` or `Display` mode. -Maybe depending on `--debug` as a CLI argument. \ No newline at end of file +Maybe depending on `--debug` as a CLI argument. diff --git a/booksrc/tutorial4.md b/booksrc/tutorial4.md index 68cc16d..f717706 100644 --- a/booksrc/tutorial4.md +++ b/booksrc/tutorial4.md @@ -1,12 +1,7 @@ -# Saving coding chars +# More information -Because decorating an error with more information should not -let you jump through hoops, `chainerror` has a quick macro for that. - -`mstrerror!()` fits right into `.map_err()` letting you quickly add -more debug strings. - -`mstrerror!()` even understands `format!()` syntax like `println!()`. +To give more context to the error, you want to use `format!` +to extend the information in the context string. ~~~rust {{#include ../examples/tutorial4.rs}} @@ -14,4 +9,4 @@ more debug strings. # mod chainerror { {{#rustdoc_include ../src/lib.rs:-1}} # } -~~~ \ No newline at end of file +~~~ diff --git a/booksrc/tutorial8.md b/booksrc/tutorial8.md index 8060788..da0c405 100644 --- a/booksrc/tutorial8.md +++ b/booksrc/tutorial8.md @@ -4,8 +4,8 @@ To distinguish the errors occuring in various places, we can define named string "new type" pattern. ~~~rust,ignore -derive_str_cherr!(Func2Error); -derive_str_cherr!(Func1Error); +derive_str_context!(Func2Error); +derive_str_context!(Func1Error); ~~~ Instead of `ChainError` we now have `struct Func1Error(String)` and `ChainError`. @@ -28,4 +28,4 @@ hiding the `ChainError` implementation detail. # mod chainerror { {{#rustdoc_include ../src/lib.rs:-1}} # } -~~~ \ No newline at end of file +~~~ diff --git a/examples/example.rs b/examples/example.rs index 4044155..cbed147 100644 --- a/examples/example.rs +++ b/examples/example.rs @@ -11,14 +11,14 @@ fn do_some_io() -> Result<(), Box> { fn func3() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(format!("Error reading '{}'", filename))?; + do_some_io().context(format!("Error reading '{}'", filename))?; Ok(()) } -derive_str_cherr!(Func2Error); +derive_str_context!(Func2Error); fn func2() -> ChainResult<(), Func2Error> { - func3().cherr(Func2Error(format!("func2 error: calling func3")))?; + func3().context(Func2Error(format!("func2 error: calling func3")))?; Ok(()) } @@ -43,9 +43,9 @@ impl ::std::fmt::Debug for Func1Error { } fn func1() -> ChainResult<(), Func1Error> { - func2().cherr(Func1Error::Func2)?; + func2().context(Func1Error::Func2)?; let filename = String::from("bar.txt"); - do_some_io().cherr(Func1Error::IO(filename))?; + do_some_io().context(Func1Error::IO(filename))?; Ok(()) } diff --git a/examples/tutorial10.rs b/examples/tutorial10.rs index 4ee8f44..5118c63 100644 --- a/examples/tutorial10.rs +++ b/examples/tutorial10.rs @@ -8,11 +8,11 @@ fn do_some_io() -> Result<(), Box> { Ok(()) } -derive_str_cherr!(Func2Error); +derive_str_context!(Func2Error); fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(Func2Error(format!("Error reading '{}'", filename)))?; + do_some_io().context(Func2Error(format!("Error reading '{}'", filename)))?; Ok(()) } @@ -33,9 +33,9 @@ impl ::std::fmt::Display for Func1ErrorKind { impl ::std::error::Error for Func1ErrorKind {} fn func1() -> ChainResult<(), Func1ErrorKind> { - func2().cherr(Func1ErrorKind::Func2)?; + func2().context(Func1ErrorKind::Func2)?; let filename = String::from("bar.txt"); - do_some_io().cherr(Func1ErrorKind::IO(filename))?; + do_some_io().context(Func1ErrorKind::IO(filename))?; Ok(()) } @@ -53,6 +53,8 @@ fn main() -> Result<(), Box> { } eprintln!("\nDebug Error:\n{:?}", e); + + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial11.rs b/examples/tutorial11.rs index 42e5de8..a943b97 100644 --- a/examples/tutorial11.rs +++ b/examples/tutorial11.rs @@ -8,11 +8,11 @@ fn do_some_io() -> Result<(), Box> { Ok(()) } -derive_str_cherr!(Func2Error); +derive_str_context!(Func2Error); fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(Func2Error(format!("Error reading '{}'", filename)))?; + do_some_io().context(Func2Error(format!("Error reading '{}'", filename)))?; Ok(()) } @@ -39,9 +39,9 @@ impl ::std::fmt::Debug for Func1ErrorKind { impl ::std::error::Error for Func1ErrorKind {} fn func1() -> ChainResult<(), Func1ErrorKind> { - func2().cherr(Func1ErrorKind::Func2)?; + func2().context(Func1ErrorKind::Func2)?; let filename = String::from("bar.txt"); - do_some_io().cherr(Func1ErrorKind::IO(filename))?; + do_some_io().context(Func1ErrorKind::IO(filename))?; Ok(()) } @@ -59,6 +59,8 @@ fn main() -> Result<(), Box> { } eprintln!("\nDebug Error:\n{:?}", e); + + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial12.rs b/examples/tutorial12.rs index ce3cea6..e2bf644 100644 --- a/examples/tutorial12.rs +++ b/examples/tutorial12.rs @@ -8,11 +8,11 @@ fn do_some_io() -> Result<(), Box> { Ok(()) } -derive_str_cherr!(Func2Error); +derive_str_context!(Func2Error); fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(Func2Error(format!("Error reading '{}'", filename)))?; + do_some_io().context(Func2Error(format!("Error reading '{}'", filename)))?; Ok(()) } @@ -39,9 +39,9 @@ impl ::std::fmt::Debug for Func1ErrorKind { impl ::std::error::Error for Func1ErrorKind {} fn func1() -> ChainResult<(), Func1ErrorKind> { - func2().cherr(Func1ErrorKind::Func2)?; + func2().context(Func1ErrorKind::Func2)?; let filename = String::from("bar.txt"); - do_some_io().cherr(Func1ErrorKind::IO(filename))?; + do_some_io().context(Func1ErrorKind::IO(filename))?; Ok(()) } @@ -70,6 +70,8 @@ fn main() -> Result<(), Box> { } eprintln!("\nDebug Error:\n{:?}", e); + + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial13.rs b/examples/tutorial13.rs index 29a0374..19bc713 100644 --- a/examples/tutorial13.rs +++ b/examples/tutorial13.rs @@ -7,11 +7,11 @@ pub mod mycrate { Ok(()) } - derive_str_cherr!(Func2Error); + derive_str_context!(Func2Error); fn func2() -> std::result::Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(Func2Error(format!("Error reading '{}'", filename)))?; + do_some_io().context(Func2Error(format!("Error reading '{}'", filename)))?; Ok(()) } @@ -35,9 +35,9 @@ pub mod mycrate { } pub fn func1() -> Result<()> { - func2().cherr(ErrorKind::Func2)?; + func2().context(ErrorKind::Func2)?; let filename = String::from("bar.txt"); - do_some_io().cherr(ErrorKind::IO(filename))?; + do_some_io().context(ErrorKind::IO(filename))?; Ok(()) } } @@ -72,6 +72,8 @@ fn main() -> Result<(), Box> { } eprintln!("\nDebug Error:\n{:?}", e); + + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial14.rs b/examples/tutorial14.rs index 84c3491..8daeceb 100644 --- a/examples/tutorial14.rs +++ b/examples/tutorial14.rs @@ -27,7 +27,7 @@ pub mod mycrate { } } - macro_rules! mcherr { + macro_rules! mcontext { ( $k:expr ) => {{ |e| { Error( @@ -92,7 +92,7 @@ pub mod mycrate { pub fn func2() -> std::result::Result<(), Error> { let filename = "foo.txt"; - do_some_io().map_err(mcherr!(ErrorKind::IO(format!( + do_some_io().map_err(mcontext!(ErrorKind::IO(format!( "Error reading '{}'", filename ))))?; @@ -115,7 +115,7 @@ pub mod mycrate { } } - macro_rules! mcherr { + macro_rules! mcontext { ( $k:expr ) => {{ |e| { Error( @@ -175,9 +175,9 @@ pub mod mycrate { pub type Result = std::result::Result; pub fn func1() -> Result<()> { - func2().map_err(mcherr!(ErrorKind::Func2))?; + func2().map_err(mcontext!(ErrorKind::Func2))?; let filename = String::from("bar.txt"); - do_some_io().map_err(mcherr!(ErrorKind::IO(filename)))?; + do_some_io().map_err(mcontext!(ErrorKind::IO(filename)))?; Ok(()) } } @@ -212,6 +212,8 @@ fn main() -> Result<(), Box> { } eprintln!("\nDebug Error:\n{:?}", e); + + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial15.rs b/examples/tutorial15.rs index 5130bfc..c045c85 100644 --- a/examples/tutorial15.rs +++ b/examples/tutorial15.rs @@ -8,11 +8,11 @@ pub mod mycrate { Ok(()) } - derive_str_cherr!(Func2Error); + derive_str_context!(Func2Error); fn func2() -> std::result::Result<(), Box> { let filename = "foo.txt"; - do_some_io(filename).cherr(Func2Error(format!("Error reading '{}'", filename)))?; + do_some_io(filename).context(Func2Error(format!("Error reading '{}'", filename)))?; Ok(()) } @@ -85,15 +85,15 @@ pub mod mycrate { let filename = "bar.txt"; - do_some_io(filename).map_cherr(|e| ErrorKind::from_io_error(&e, filename.into()))?; - do_some_io(filename).map_cherr(|_| ErrorKind::IO(filename.into()))?; - do_some_io(filename).map_cherr(|e| ErrorKind::from(e))?; + do_some_io(filename).map_context(|e| ErrorKind::from_io_error(&e, filename.into()))?; + do_some_io(filename).map_context(|_| ErrorKind::IO(filename.into()))?; + do_some_io(filename).map_context(|e| ErrorKind::from(e))?; Ok(()) } pub fn super_func1() -> Result<()> { - func1().map_cherr(|e| ErrorKind::from(e))?; + func1().map_context(|e| ErrorKind::from(e))?; Ok(()) } } @@ -130,6 +130,8 @@ fn main() -> Result<(), Box> { } eprintln!("\nDebug Error:\n{:?}", e); + + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial2.rs b/examples/tutorial2.rs index 140862f..8c68dc0 100644 --- a/examples/tutorial2.rs +++ b/examples/tutorial2.rs @@ -11,14 +11,14 @@ fn do_some_io() -> Result<(), Box> { fn func2() -> Result<(), Box> { if let Err(e) = do_some_io() { - Err(e).cherr("func2 error")?; + Err(e).context("func2 error")?; } Ok(()) } fn func1() -> Result<(), Box> { if let Err(e) = func2() { - Err(e).cherr("func1 error")?; + Err(e).context("func1 error")?; } Ok(()) } diff --git a/examples/tutorial3.rs b/examples/tutorial3.rs index 9096e07..8475d6f 100644 --- a/examples/tutorial3.rs +++ b/examples/tutorial3.rs @@ -10,18 +10,19 @@ fn do_some_io() -> Result<(), Box> { } fn func2() -> Result<(), Box> { - do_some_io().cherr("func2 error")?; + do_some_io().context("func2 error")?; Ok(()) } fn func1() -> Result<(), Box> { - func2().cherr("func1 error")?; + func2().context("func1 error")?; Ok(()) } fn main() -> Result<(), Box> { if let Err(e) = func1() { eprintln!("{:?}", e); + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial4.rs b/examples/tutorial4.rs index 3b5fc15..d1b247b 100644 --- a/examples/tutorial4.rs +++ b/examples/tutorial4.rs @@ -10,18 +10,19 @@ fn do_some_io() -> Result<(), Box> { fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(format!("Error reading '{}'", filename))?; + do_some_io().context(format!("Error reading '{}'", filename))?; Ok(()) } fn func1() -> Result<(), Box> { - func2().cherr("func1 error")?; + func2().context("func1 error")?; Ok(()) } fn main() -> Result<(), Box> { if let Err(e) = func1() { eprintln!("{:?}", e); + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial5.rs b/examples/tutorial5.rs index edabbbf..333208c 100644 --- a/examples/tutorial5.rs +++ b/examples/tutorial5.rs @@ -10,7 +10,7 @@ fn do_some_io() -> Result<(), Box> { fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(format!("Error reading '{}'", filename))?; + do_some_io().context(format!("Error reading '{}'", filename))?; Ok(()) } @@ -18,7 +18,7 @@ fn func1() -> Result<(), Box> { if let Err(e) = func2() { if let Some(s) = e.source() { eprintln!("func2 failed because of '{}'", s); - Err(e).cherr("func1 error")?; + Err(e).context("func1 error")?; } } Ok(()) @@ -27,6 +27,7 @@ fn func1() -> Result<(), Box> { fn main() -> Result<(), Box> { if let Err(e) = func1() { eprintln!("{}", e); + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial6.rs b/examples/tutorial6.rs index f8c6549..9310c8c 100644 --- a/examples/tutorial6.rs +++ b/examples/tutorial6.rs @@ -10,12 +10,12 @@ fn do_some_io() -> Result<(), Box> { fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(format!("Error reading '{}'", filename))?; + do_some_io().context(format!("Error reading '{}'", filename))?; Ok(()) } fn func1() -> Result<(), Box> { - func2().cherr("func1 error")?; + func2().context("func1 error")?; Ok(()) } @@ -35,6 +35,7 @@ fn main() -> Result<(), Box> { } s = c; } + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial7.rs b/examples/tutorial7.rs index 11658f2..feb7cf8 100644 --- a/examples/tutorial7.rs +++ b/examples/tutorial7.rs @@ -10,12 +10,12 @@ fn do_some_io() -> Result<(), Box> { fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(format!("Error reading '{}'", filename))?; + do_some_io().context(format!("Error reading '{}'", filename))?; Ok(()) } fn func1() -> Result<(), Box> { - func2().cherr(format!("func1 error"))?; + func2().context(format!("func1 error"))?; Ok(()) } @@ -36,6 +36,7 @@ fn main() -> Result<(), Box> { eprintln!("The root cause was: std::io::Error: {:#?}", ioerror); } } + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial8.rs b/examples/tutorial8.rs index f55b83b..2093782 100644 --- a/examples/tutorial8.rs +++ b/examples/tutorial8.rs @@ -8,18 +8,18 @@ fn do_some_io() -> Result<(), Box> { Ok(()) } -derive_str_cherr!(Func2Error); +derive_str_context!(Func2Error); fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(Func2Error(format!("Error reading '{}'", filename)))?; + do_some_io().context(Func2Error(format!("Error reading '{}'", filename)))?; Ok(()) } -derive_str_cherr!(Func1Error); +derive_str_context!(Func1Error); fn func1() -> Result<(), Box> { - func2().cherr(Func1Error(format!("func1 error")))?; + func2().context(Func1Error(format!("func1 error")))?; Ok(()) } @@ -36,6 +36,7 @@ fn main() -> Result<(), Box> { eprintln!("Debug Func2Error:\n{:?}", f2err); } } + std::process::exit(1); } Ok(()) } diff --git a/examples/tutorial9.rs b/examples/tutorial9.rs index 374cb77..1561535 100644 --- a/examples/tutorial9.rs +++ b/examples/tutorial9.rs @@ -8,21 +8,21 @@ fn do_some_io() -> Result<(), Box> { Ok(()) } -derive_str_cherr!(Func2Error); +derive_str_context!(Func2Error); fn func2() -> Result<(), Box> { let filename = "foo.txt"; - do_some_io().cherr(Func2Error(format!("Error reading '{}'", filename)))?; + do_some_io().context(Func2Error(format!("Error reading '{}'", filename)))?; Ok(()) } -derive_str_cherr!(Func1ErrorFunc2); -derive_str_cherr!(Func1ErrorIO); +derive_str_context!(Func1ErrorFunc2); +derive_str_context!(Func1ErrorIO); fn func1() -> Result<(), Box> { - func2().cherr(Func1ErrorFunc2(format!("func1 error calling func2")))?; + func2().context(Func1ErrorFunc2(format!("func1 error calling func2")))?; let filename = "bar.txt"; - do_some_io().cherr(Func1ErrorIO(format!("Error reading '{}'", filename)))?; + do_some_io().context(Func1ErrorIO(format!("Error reading '{}'", filename)))?; Ok(()) } @@ -35,6 +35,7 @@ fn main() -> Result<(), Box> { if let Some(s) = e.downcast_chain_ref::() { eprintln!("Func1ErrorFunc2:\n{:?}", s); } + std::process::exit(1); } Ok(()) } diff --git a/src/lib.rs b/src/lib.rs index 4c81ee2..0837a64 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -12,18 +12,9 @@ //! //! ## Features //! -//! `default = [ "location", "debug-cause" ]` -//! -//! `location` -//! : store the error location -//! //! `display-cause` //! : turn on printing a backtrace of the errors in `Display` //! -//! `debug-cause` -//! : print a backtrace of the errors in `Debug` -//! -//! //! # Tutorial //! //! Read the [Tutorial](https://haraldh.github.io/chainerror/tutorial1.html) @@ -91,17 +82,16 @@ //! //! fn func2() -> Result<(), Box> { //! let filename = "foo.txt"; -//! do_some_io().cherr(format!("Error reading '{}'", filename))?; +//! do_some_io().context(format!("Error reading '{}'", filename))?; //! Ok(()) //! } //! //! fn func1() -> Result<(), Box> { -//! func2().cherr("func1 error")?; +//! func2().context("func1 error")?; //! Ok(()) //! } //! //! if let Err(e) = func1() { -//! # #[cfg(feature = "debug-cause")] //! #[cfg(not(windows))] //! assert_eq!( //! format!("\n{:?}\n", e), @@ -133,14 +123,14 @@ //! //! fn func3() -> Result<(), Box> { //! let filename = "foo.txt"; -//! do_some_io().cherr(format!("Error reading '{}'", filename))?; +//! do_some_io().context(format!("Error reading '{}'", filename))?; //! Ok(()) //! } //! -//! derive_str_cherr!(Func2Error); +//! derive_str_context!(Func2Error); //! //! fn func2() -> ChainResult<(), Func2Error> { -//! func3().cherr(Func2Error("func2 error: calling func3".into()))?; +//! func3().context(Func2Error("func2 error: calling func3".into()))?; //! Ok(()) //! } //! @@ -165,9 +155,9 @@ //! } //! //! fn func1() -> ChainResult<(), Func1Error> { -//! func2().cherr(Func1Error::Func2)?; +//! func2().context(Func1Error::Func2)?; //! let filename = String::from("bar.txt"); -//! do_some_io().cherr(Func1Error::IO(filename))?; +//! do_some_io().context(Func1Error::IO(filename))?; //! Ok(()) //! } //! @@ -196,7 +186,6 @@ //! eprintln!("\nThe root cause was: std::io::Error: {:#?}", io_error); //! } //! -//! # #[cfg(feature = "no-debug-cause")] //! #[cfg(not(windows))] //! assert_eq!( //! format!("\n{:?}\n", e), @@ -229,15 +218,15 @@ pub mod prelude { //! convenience prelude pub mod v1 { //! convenience prelude - pub use crate::ChainErrorDown as _; - pub use crate::ResultTrait as _; - pub use crate::{derive_err_kind, derive_str_cherr, ChainError, ChainResult}; + pub use super::super::ChainErrorDown as _; + pub use super::super::ResultTrait as _; + pub use super::super::{ChainError, ChainResult}; + pub use crate::{derive_err_kind, derive_str_context}; } } /// chains an inner error kind `T` with a causing error pub struct ChainError { - #[cfg(feature = "location")] occurrence: Option, kind: T, error_cause: Option>, @@ -247,8 +236,7 @@ pub struct ChainError { pub type ChainResult = std::result::Result>; impl ChainError { - #[cfg(feature = "location")] - /// Use the `cherr()` or `map_cherr()` Result methods instead of calling this directly + /// Use the `context()` or `map_context()` Result methods instead of calling this directly #[inline] pub fn new( kind: T, @@ -262,17 +250,6 @@ impl ChainError { } } - #[cfg(not(feature = "location"))] - /// Use the `cherr()` or `map_cherr()` Result methods instead of calling this directly - #[inline] - pub fn new( - kind: T, - error_cause: Option>, - _occurrence: Option, - ) -> Self { - Self { kind, error_cause } - } - /// return the root cause of the error chain, if any exists pub fn root_cause(&self) -> Option<&(dyn Error + 'static)> { self.iter().last() @@ -292,18 +269,18 @@ impl ChainError { /// Ok(()) /// } /// - /// derive_str_cherr!(Func2Error); + /// derive_str_context!(Func2Error); /// /// fn func2() -> Result<(), Box> { /// let filename = "foo.txt"; - /// do_some_io().cherr(Func2Error(format!("Error reading '{}'", filename)))?; + /// do_some_io().context(Func2Error(format!("Error reading '{}'", filename)))?; /// Ok(()) /// } /// - /// derive_str_cherr!(Func1Error); + /// derive_str_context!(Func1Error); /// /// fn func1() -> Result<(), Box> { - /// func2().cherr(Func1Error("func1 error".into()))?; + /// func2().context(Func1Error("func1 error".into()))?; /// Ok(()) /// } /// @@ -334,7 +311,7 @@ impl ChainError { /// /// ```rust /// # use chainerror::prelude::v1::*; - /// # derive_str_cherr!(FooError); + /// # derive_str_context!(FooError); /// # let err = ChainError::new(String::new(), None, None); /// // Instead of writing /// err.find_cause::>(); @@ -357,7 +334,7 @@ impl ChainError { /// /// ```rust /// # use chainerror::prelude::v1::*; - /// # derive_str_cherr!(FooErrorKind); + /// # derive_str_context!(FooErrorKind); /// # let err = ChainError::new(String::new(), None, None); /// // Instead of writing /// err.find_cause::>(); @@ -394,11 +371,11 @@ impl ChainError { /// Ok(()) /// } /// - /// derive_str_cherr!(Func2Error); + /// derive_str_context!(Func2Error); /// /// fn func2() -> Result<(), Box> { /// let filename = "foo.txt"; - /// do_some_io().cherr(Func2Error(format!("Error reading '{}'", filename)))?; + /// do_some_io().context(Func2Error(format!("Error reading '{}'", filename)))?; /// Ok(()) /// } /// @@ -419,8 +396,8 @@ impl ChainError { /// # } /// /// fn func1() -> ChainResult<(), Func1ErrorKind> { - /// func2().cherr(Func1ErrorKind::Func2)?; - /// do_some_io().cherr(Func1ErrorKind::IO("bar.txt".into()))?; + /// func2().context(Func1ErrorKind::Func2)?; + /// do_some_io().context(Func1ErrorKind::IO("bar.txt".into()))?; /// Ok(()) /// } /// @@ -453,10 +430,10 @@ impl ChainError { /// Convenience methods for `Result<>` to turn the error into a decorated ChainError pub trait ResultTrait>> { /// Decorate the error with a `kind` of type `T` and the source `Location` - fn cherr(self, kind: T) -> std::result::Result>; + fn context(self, kind: T) -> std::result::Result>; - /// Decorate the error with a `kind` of type `T` produced with a `FnOnce` and the source `Location` - fn map_cherr T>( + /// Decorate the `error` with a `kind` of type `T` produced with a `FnOnce(&error)` and the source `Location` + fn map_context T>( self, op: F, ) -> std::result::Result>; @@ -466,7 +443,7 @@ impl>> ResultTrait for std::result::Result { #[track_caller] - fn cherr(self, kind: T) -> std::result::Result> { + fn context(self, kind: T) -> std::result::Result> { match self { Ok(t) => Ok(t), Err(error_cause) => Err(ChainError::new( @@ -478,7 +455,7 @@ impl>> ResultTrait } #[track_caller] - fn map_cherr T>( + fn map_context T>( self, op: F, ) -> std::result::Result> { @@ -741,21 +718,15 @@ impl Debug for ChainError { if f.alternate() { let mut f = f.debug_struct(&format!("ChainError<{}>", std::any::type_name::())); - #[cfg(feature = "location")] - let f = f.field("occurrence", &self.occurrence); - - let f = f.field("kind", &self.kind); - - #[cfg(feature = "debug-cause")] - let f = f.field("source", &self.source()); + let f = f + .field("occurrence", &self.occurrence) + .field("kind", &self.kind) + .field("source", &self.source()); f.finish() } else { - #[cfg(feature = "location")] - { - if let Some(ref o) = self.occurrence { - write!(f, "{}: ", o)?; - } + if let Some(ref o) = self.occurrence { + write!(f, "{}: ", o)?; } if TypeId::of::() == TypeId::of::() @@ -766,12 +737,9 @@ impl Debug for ChainError { Debug::fmt(&self.kind, f)?; } - #[cfg(feature = "debug-cause")] - { - if let Some(e) = self.source() { - writeln!(f, "\nCaused by:")?; - Debug::fmt(&e, f)?; - } + if let Some(e) = self.source() { + writeln!(f, "\nCaused by:")?; + Debug::fmt(&e, f)?; } Ok(()) } @@ -825,18 +793,18 @@ where /// # Err(io::Error::from(io::ErrorKind::NotFound))?; /// # Ok(()) /// # } -/// derive_str_cherr!(Func2Error); +/// derive_str_context!(Func2Error); /// /// fn func2() -> ChainResult<(), Func2Error> { /// let filename = "foo.txt"; -/// do_some_io().cherr(Func2Error(format!("Error reading '{}'", filename)))?; +/// do_some_io().context(Func2Error(format!("Error reading '{}'", filename)))?; /// Ok(()) /// } /// -/// derive_str_cherr!(Func1Error); +/// derive_str_context!(Func1Error); /// /// fn func1() -> Result<(), Box> { -/// func2().cherr(Func1Error("func1 error".into()))?; +/// func2().context(Func1Error("func1 error".into()))?; /// Ok(()) /// } /// # if let Err(e) = func1() { @@ -851,7 +819,7 @@ where /// # } /// ``` #[macro_export] -macro_rules! derive_str_cherr { +macro_rules! derive_str_context { ($e:ident) => { #[derive(Clone)] pub struct $e(pub String); @@ -928,9 +896,9 @@ macro_rules! derive_str_cherr { /// let filename = "bar.txt"; /// /// do_some_io(filename) -/// .map_cherr(|e| ErrorKind::from_io_error(e, filename.into()))?; -/// do_some_io(filename).map_cherr(|e| ErrorKind::IO(filename.into()))?; -/// do_some_io(filename).map_cherr(|e| ErrorKind::from(e))?; +/// .map_context(|e| ErrorKind::from_io_error(e, filename.into()))?; +/// do_some_io(filename).map_context(|e| ErrorKind::IO(filename.into()))?; +/// do_some_io(filename).map_context(|e| ErrorKind::from(e))?; /// Ok(()) /// } /// ``` diff --git a/tests/test_iter.rs b/tests/test_iter.rs index b567544..318c7a7 100644 --- a/tests/test_iter.rs +++ b/tests/test_iter.rs @@ -7,12 +7,12 @@ use std::io; fn test_iter() -> Result<(), Box> { use std::fmt::Write; let err: Result<(), _> = Err(io::Error::from(io::ErrorKind::NotFound)); - let err = err.cherr("1"); - let err = err.cherr("2"); - let err = err.cherr("3"); - let err = err.cherr("4"); - let err = err.cherr("5"); - let err = err.cherr("6"); + let err = err.context("1"); + let err = err.context("2"); + let err = err.context("3"); + let err = err.context("4"); + let err = err.context("5"); + let err = err.context("6"); let err = err.err().unwrap(); let mut res = String::new(); @@ -36,12 +36,12 @@ fn test_iter() -> Result<(), Box> { #[test] fn test_iter() -> Result<(), Box> { let err: Result<(), _> = Err(io::Error::from(io::ErrorKind::NotFound)); - let err = err.cherr("1"); - let err = err.cherr("2"); - let err = err.cherr("3"); - let err = err.cherr("4"); - let err = err.cherr("5"); - let err = err.cherr("6"); + let err = err.context("1"); + let err = err.context("2"); + let err = err.context("3"); + let err = err.context("4"); + let err = err.context("5"); + let err = err.context("6"); let err = err.err().unwrap(); let res = err.to_string(); @@ -61,12 +61,12 @@ fn test_iter() -> Result<(), Box> { #[test] fn test_find_cause() -> Result<(), Box> { let err: Result<(), _> = Err(io::Error::from(io::ErrorKind::NotFound)); - let err = err.cherr("1"); - let err = err.cherr("2"); - let err = err.cherr("3"); - let err = err.cherr("4"); - let err = err.cherr("5"); - let err = err.cherr("6"); + let err = err.context("1"); + let err = err.context("2"); + let err = err.context("3"); + let err = err.context("4"); + let err = err.context("5"); + let err = err.context("6"); let err = err.err().unwrap(); let io_error: Option<&io::Error> = err.find_cause::(); @@ -79,12 +79,12 @@ fn test_find_cause() -> Result<(), Box> { #[test] fn test_root_cause() -> Result<(), Box> { let err: Result<(), _> = Err(io::Error::from(io::ErrorKind::NotFound)); - let err = err.cherr("1"); - let err = err.cherr("2"); - let err = err.cherr("3"); - let err = err.cherr("4"); - let err = err.cherr("5"); - let err = err.cherr("6"); + let err = err.context("1"); + let err = err.context("2"); + let err = err.context("3"); + let err = err.context("4"); + let err = err.context("5"); + let err = err.context("6"); let err = err.err().unwrap(); let err: Option<&(dyn std::error::Error + 'static)> = err.root_cause();