testutils/
traits.rs

1pub use tap::{Pipe, Tap};
2
3/// Extension trait for types that can be converted into a bool.
4pub trait BoolExt {
5  /// Converts the bool value into a `Result<(), E>`.
6  ///
7  /// If the value is `true`, it returns `Ok(())`. If the value is `false`, it
8  /// returns `Err(err())`.
9  ///
10  /// # Examples
11  ///
12  /// ## Simple
13  ///
14  /// ```
15  /// use testutils::traits::BoolExt;
16  ///
17  /// let value = true;
18  /// let res: Result<(), &str> = value.ok_or_else(|| "error");
19  /// assert_eq!(res, Ok(()));
20  ///
21  /// let value = false;
22  /// assert_eq!(value.ok_or_else(|| "error"), Err("error"));
23  /// ```
24  ///
25  /// ## A more complex example
26  ///
27  /// ```ignore
28  /// use testutils::traits::Pipe;
29  /// use testutils::get_pkg_name;
30  /// use testutils::testutils::traits::BoolExt;
31  /// use std::io;
32  ///
33  /// let err = || "Failed to run `cargo rustdoc` command".pipe(io::Error::other);
34  ///
35  /// get_pkg_name!()
36  ///  .pipe(build_rsdoc)? // ExitStatus
37  ///  .success() // bool
38  ///  .ok_or_else(err) // io::Result<()>
39  /// ```
40  fn ok_or_else<E>(self, err: impl FnOnce() -> E) -> Result<(), E>
41  where
42    Self: Into<bool>,
43  {
44    if self.into() { Ok(()) } else { Err(err()) }
45  }
46}
47
48impl BoolExt for bool {}
49
50#[cfg(test)]
51mod tests {
52  use tap::TapOptional;
53
54  use super::*;
55
56  #[ignore]
57  #[test]
58  fn test_tap_opt() {
59    let opt = Some(42);
60    opt.tap_some(|&x| assert_eq!(x, 42));
61    opt.map(|x| assert_eq!(x, 42));
62  }
63
64  #[ignore]
65  #[test]
66  fn test_bool_ok_or_else() {
67    let value = true;
68    let res: Result<(), &str> = value.ok_or_else(|| "error");
69    assert_eq!(res, Ok(()));
70
71    let value = false;
72    assert_eq!(value.ok_or_else(|| "error"), Err("error"));
73  }
74
75  #[cfg(feature = "std")]
76  #[ignore]
77  #[test]
78  fn test_bool_ok_or_std_io_error() {
79    // use std::io;
80  }
81}