1 | /// List of all errors. |
2 | #[derive (Debug, PartialEq, Eq)] |
3 | pub enum Error { |
4 | /// An input data ended earlier than expected. |
5 | /// |
6 | /// Should only appear on invalid input data. |
7 | /// Errors in a valid XML should be handled by errors below. |
8 | UnexpectedEndOfStream, |
9 | |
10 | /// An input text contains unknown data. |
11 | UnexpectedData(usize), |
12 | |
13 | /// A provided string doesn't have a valid data. |
14 | /// |
15 | /// For example, if we try to parse a color form `zzz` |
16 | /// string - we will get this error. |
17 | /// But if we try to parse a number list like `1.2 zzz`, |
18 | /// then we will get `InvalidNumber`, because at least some data is valid. |
19 | InvalidValue, |
20 | |
21 | /// An invalid ident. |
22 | /// |
23 | /// CSS idents have certain rules with regard to the characters they may contain. |
24 | /// For example, they may not start with a number. If an invalid ident is encountered, |
25 | /// this error will be returned. |
26 | InvalidIdent, |
27 | |
28 | /// An invalid/unexpected character. |
29 | /// |
30 | /// The first byte is an actual one, others - expected. |
31 | /// |
32 | /// We are using a single value to reduce the struct size. |
33 | InvalidChar(Vec<u8>, usize), |
34 | |
35 | /// An unexpected character instead of an XML space. |
36 | /// |
37 | /// The first string is an actual one, others - expected. |
38 | /// |
39 | /// We are using a single value to reduce the struct size. |
40 | InvalidString(Vec<String>, usize), |
41 | |
42 | /// An invalid number. |
43 | InvalidNumber(usize), |
44 | } |
45 | |
46 | impl std::fmt::Display for Error { |
47 | fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { |
48 | match *self { |
49 | Error::UnexpectedEndOfStream => { |
50 | write!(f, "unexpected end of stream" ) |
51 | } |
52 | Error::UnexpectedData(pos) => { |
53 | write!(f, "unexpected data at position {}" , pos) |
54 | } |
55 | Error::InvalidValue => { |
56 | write!(f, "invalid value" ) |
57 | } |
58 | Error::InvalidIdent => { |
59 | write!(f, "invalid ident" ) |
60 | } |
61 | Error::InvalidChar(ref chars, pos) => { |
62 | // Vec<u8> -> Vec<String> |
63 | let list: Vec<String> = chars |
64 | .iter() |
65 | .skip(1) |
66 | .map(|c| String::from_utf8(vec![*c]).unwrap()) |
67 | .collect(); |
68 | |
69 | write!( |
70 | f, |
71 | "expected ' {}' not ' {}' at position {}" , |
72 | list.join("', '" ), |
73 | chars[0] as char, |
74 | pos |
75 | ) |
76 | } |
77 | Error::InvalidString(ref strings, pos) => { |
78 | write!( |
79 | f, |
80 | "expected ' {}' not ' {}' at position {}" , |
81 | strings[1..].join("', '" ), |
82 | strings[0], |
83 | pos |
84 | ) |
85 | } |
86 | Error::InvalidNumber(pos) => { |
87 | write!(f, "invalid number at position {}" , pos) |
88 | } |
89 | } |
90 | } |
91 | } |
92 | |
93 | impl std::error::Error for Error { |
94 | fn description(&self) -> &str { |
95 | "an SVG data parsing error" |
96 | } |
97 | } |
98 | |