anyhow/
macros.rs

1/// Return early with an error.
2///
3/// This macro is equivalent to
4/// <code>return Err([anyhow!($args\...)][anyhow!])</code>.
5///
6/// The surrounding function's or closure's return value is required to be
7/// <code>Result&lt;_, [anyhow::Error][crate::Error]&gt;</code>.
8///
9/// [anyhow!]: crate::anyhow
10///
11/// # Example
12///
13/// ```
14/// # use anyhow::{bail, Result};
15/// #
16/// # fn has_permission(user: usize, resource: usize) -> bool {
17/// #     true
18/// # }
19/// #
20/// # fn main() -> Result<()> {
21/// #     let user = 0;
22/// #     let resource = 0;
23/// #
24/// if !has_permission(user, resource) {
25///     bail!("permission denied for accessing {}", resource);
26/// }
27/// #     Ok(())
28/// # }
29/// ```
30///
31/// ```
32/// # use anyhow::{bail, Result};
33/// # use thiserror::Error;
34/// #
35/// # const MAX_DEPTH: usize = 1;
36/// #
37/// #[derive(Error, Debug)]
38/// enum ScienceError {
39///     #[error("recursion limit exceeded")]
40///     RecursionLimitExceeded,
41///     # #[error("...")]
42///     # More = (stringify! {
43///     ...
44///     # }, 1).1,
45/// }
46///
47/// # fn main() -> Result<()> {
48/// #     let depth = 0;
49/// #
50/// if depth > MAX_DEPTH {
51///     bail!(ScienceError::RecursionLimitExceeded);
52/// }
53/// #     Ok(())
54/// # }
55/// ```
56#[macro_export]
57macro_rules! bail {
58    ($msg:literal $(,)?) => {
59        return $crate::__private::Err($crate::__anyhow!($msg))
60    };
61    ($err:expr $(,)?) => {
62        return $crate::__private::Err($crate::__anyhow!($err))
63    };
64    ($fmt:expr, $($arg:tt)*) => {
65        return $crate::__private::Err($crate::__anyhow!($fmt, $($arg)*))
66    };
67}
68
69macro_rules! __ensure {
70    ($ensure:item) => {
71        /// Return early with an error if a condition is not satisfied.
72        ///
73        /// This macro is equivalent to
74        /// <code>if !$cond { return Err([anyhow!($args\...)][anyhow!]); }</code>.
75        ///
76        /// The surrounding function's or closure's return value is required to be
77        /// <code>Result&lt;_, [anyhow::Error][crate::Error]&gt;</code>.
78        ///
79        /// Analogously to `assert!`, `ensure!` takes a condition and exits the function
80        /// if the condition fails. Unlike `assert!`, `ensure!` returns an `Error`
81        /// rather than panicking.
82        ///
83        /// [anyhow!]: crate::anyhow
84        ///
85        /// # Example
86        ///
87        /// ```
88        /// # use anyhow::{ensure, Result};
89        /// #
90        /// # fn main() -> Result<()> {
91        /// #     let user = 0;
92        /// #
93        /// ensure!(user == 0, "only user 0 is allowed");
94        /// #     Ok(())
95        /// # }
96        /// ```
97        ///
98        /// ```
99        /// # use anyhow::{ensure, Result};
100        /// # use thiserror::Error;
101        /// #
102        /// # const MAX_DEPTH: usize = 1;
103        /// #
104        /// #[derive(Error, Debug)]
105        /// enum ScienceError {
106        ///     #[error("recursion limit exceeded")]
107        ///     RecursionLimitExceeded,
108        ///     # #[error("...")]
109        ///     # More = (stringify! {
110        ///     ...
111        ///     # }, 1).1,
112        /// }
113        ///
114        /// # fn main() -> Result<()> {
115        /// #     let depth = 0;
116        /// #
117        /// ensure!(depth <= MAX_DEPTH, ScienceError::RecursionLimitExceeded);
118        /// #     Ok(())
119        /// # }
120        /// ```
121        $ensure
122    };
123}
124
125#[cfg(doc)]
126__ensure![
127    #[macro_export]
128    macro_rules! ensure {
129        ($cond:expr $(,)?) => {
130            if !$cond {
131                return $crate::__private::Err($crate::Error::msg(
132                    $crate::__private::concat!("Condition failed: `", $crate::__private::stringify!($cond), "`")
133                ));
134            }
135        };
136        ($cond:expr, $msg:literal $(,)?) => {
137            if !$cond {
138                return $crate::__private::Err($crate::__anyhow!($msg));
139            }
140        };
141        ($cond:expr, $err:expr $(,)?) => {
142            if !$cond {
143                return $crate::__private::Err($crate::__anyhow!($err));
144            }
145        };
146        ($cond:expr, $fmt:expr, $($arg:tt)*) => {
147            if !$cond {
148                return $crate::__private::Err($crate::__anyhow!($fmt, $($arg)*));
149            }
150        };
151    }
152];
153
154#[cfg(not(doc))]
155__ensure![
156    #[macro_export]
157    macro_rules! ensure {
158        ($($tt:tt)*) => {
159            $crate::__parse_ensure!(
160                /* state */ 0
161                /* stack */ ()
162                /* bail */ ($($tt)*)
163                /* fuel */ (~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~ ~~~~~~~~~~)
164                /* parse */ {()}
165                /* dup */ ($($tt)*)
166                /* rest */ $($tt)*
167            )
168        };
169    }
170];
171
172/// Construct an ad-hoc error from a string or existing non-`anyhow` error
173/// value.
174///
175/// This evaluates to an [`Error`][crate::Error]. It can take either just a
176/// string, or a format string with arguments. It also can take any custom type
177/// which implements `Debug` and `Display`.
178///
179/// If called with a single argument whose type implements `std::error::Error`
180/// (in addition to `Debug` and `Display`, which are always required), then that
181/// Error impl's `source` is preserved as the `source` of the resulting
182/// `anyhow::Error`.
183///
184/// # Example
185///
186/// ```
187/// # type V = ();
188/// #
189/// use anyhow::{anyhow, Result};
190///
191/// fn lookup(key: &str) -> Result<V> {
192///     if key.len() != 16 {
193///         return Err(anyhow!("key length must be 16 characters, got {:?}", key));
194///     }
195///
196///     // ...
197///     # Ok(())
198/// }
199/// ```
200#[macro_export]
201macro_rules! anyhow {
202    ($msg:literal $(,)?) => {
203        $crate::__private::must_use({
204            let error = $crate::__private::format_err($crate::__private::format_args!($msg));
205            error
206        })
207    };
208    ($err:expr $(,)?) => {
209        $crate::__private::must_use({
210            use $crate::__private::kind::*;
211            let error = match $err {
212                error => (&error).anyhow_kind().new(error),
213            };
214            error
215        })
216    };
217    ($fmt:expr, $($arg:tt)*) => {
218        $crate::Error::msg($crate::__private::format!($fmt, $($arg)*))
219    };
220}
221
222// Not public API. This is used in the implementation of some of the other
223// macros, in which the must_use call is not needed because the value is known
224// to be used.
225#[doc(hidden)]
226#[macro_export]
227macro_rules! __anyhow {
228    ($msg:literal $(,)?) => ({
229        let error = $crate::__private::format_err($crate::__private::format_args!($msg));
230        error
231    });
232    ($err:expr $(,)?) => ({
233        use $crate::__private::kind::*;
234        let error = match $err {
235            error => (&error).anyhow_kind().new(error),
236        };
237        error
238    });
239    ($fmt:expr, $($arg:tt)*) => {
240        $crate::Error::msg($crate::__private::format!($fmt, $($arg)*))
241    };
242}