Skip to main content

svgtypes/
error.rs

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