bitcoin_internals/error/parse_error.rs
1//! Contains helpers for parsing-related errors.
2
3/// Creates an error type intended for string parsing errors.
4///
5/// The resulting error type has two fields: `input` and `source`. The type of `input` is
6/// [`InputString`](super::InputString), the type of `source` is specified as the second argument
7/// to the macro.
8///
9/// The resulting type is public, conditionally implements [`std::error::Error`] and has a private
10/// `new()` method for convenience.
11///
12/// # Parameters
13///
14/// * `name` - the name of the error type
15/// * `source` - the type of the source type
16/// * `subject` - English description of the type being parsed (e.g. "a bitcoin amount")
17/// * `derive` - list of derives to add
18#[macro_export]
19macro_rules! parse_error_type {
20 ($vis:vis $name:ident, $source:ty, $subject:expr $(, $derive:path)* $(,)?) => {
21 #[derive(Debug $(, $derive)*)]
22 $vis struct $name {
23 input: $crate::error::InputString,
24 source: $source,
25 }
26
27 impl $name {
28 /// Creates `Self`.
29 fn new<T: Into<$crate::error::InputString>>(input: T, source: $source) -> Self {
30 $name {
31 input: input.into(),
32 source,
33 }
34 }
35 }
36
37 impl core::fmt::Display for $name {
38 fn fmt(&self, f: &mut core::fmt::Formatter) -> core::fmt::Result {
39 $crate::error::write_err!(f, "{}", self.input.display_cannot_parse($subject); self.source)
40 }
41 }
42
43 #[cfg(feature = "std")]
44 impl std::error::Error for $name {
45 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> { Some(&self.source) }
46 }
47 }
48}