1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
use std;
use std::fmt::{self, Debug, Display, Formatter};
#[derive(Debug)]
pub struct Error {
pub got: String,
pub kind: ErrorKind,
}
#[derive(Debug)]
pub enum ErrorKind {
MustEq { to: String },
MustNotEq { to: String },
MustBeOk,
MustBeErr,
MustBeSome,
MustBeNone,
MustHaveLength { len: usize },
MustBeEmpty,
MustBeInRange { range: String },
MustNotBeInRange { range: String },
MustBeLowercase,
MustBeUppercase,
MustBeAscii,
MustBeEqAsciiIgnoreCase { to: String },
MustBeLessThan { other: String },
MustBeLessThanOrEqual { other: String },
MustBeGreaterThan { other: String },
MustBeGreaterThanOrEqual { other: String },
MustBeNan,
MustNotBeNan,
Msg(String),
Error(Box<std::error::Error>),
}
impl Display for ErrorKind {
fn fmt(&self, f: &mut Formatter) -> fmt::Result {
use self::ErrorKind::*;
match self {
&MustEq { ref to } => write!(f, "must be {}", to),
&MustNotEq { ref to } => write!(f, "must not be {}", to),
&MustBeOk => write!(f, "must be ok"),
&MustBeErr => write!(f, "must be err"),
&MustBeSome => write!(f, "must be some"),
&MustBeNone => write!(f, "must be none"),
&MustHaveLength { len } => write!(f, "must have length {}", len),
&MustBeEmpty => write!(f, "must be empty"),
&MustBeInRange { ref range } => write!(f, "must be in range {}", range),
&MustNotBeInRange { ref range } => write!(f, "must not be in range {}", range),
&MustBeLowercase => write!(f, "must be lowercase"),
&MustBeUppercase => write!(f, "must be uppercase"),
&MustBeAscii => write!(f, "must be ascii"),
&MustBeEqAsciiIgnoreCase { ref to } => write!(f, "must eq ignore ascii case {}", to),
&MustBeLessThan { ref other } => write!(f, "must be less than {}", other),
&MustBeLessThanOrEqual { ref other } => {
write!(f, "must be less than or equal {}", other)
}
&MustBeGreaterThan { ref other } => write!(f, "must be greater than {}", other),
&MustBeGreaterThanOrEqual { ref other } => {
write!(f, "must be greater than or equal to {}", other)
}
&MustBeNan => write!(f, "must be NAN"),
&MustNotBeNan => write!(f, "must not be NAN"),
&Msg(ref msg) => write!(f, "{}", msg),
&Error(ref err) => write!(f, "{}", err.description()),
}
}
}
pub fn dump<T: Debug>(t: T) -> String {
format!("{:?}", t)
}
pub trait FromError {
fn from_err(err: ErrorKind, got: String) -> Self;
}
impl ErrorKind {
pub fn but_got<T: Debug, R: FromError>(self, got: T) -> R {
R::from_err(self, dump(got))
}
}
impl<O: Debug> FromError for Result<O, Error> {
fn from_err(err: ErrorKind, got: String) -> Self {
Err(Error {
got: got,
kind: err,
})
}
}