dcbor_pattern/
error.rs

1use logos::Span;
2use thiserror::Error;
3
4use crate::parse::Token;
5
6/// Errors that can occur during parsing of dCBOR patterns.
7#[derive(Debug, Clone, Error, PartialEq, Default)]
8pub enum Error {
9    #[error("Empty input")]
10    EmptyInput,
11
12    #[error("Unexpected end of input")]
13    UnexpectedEndOfInput,
14
15    #[error("Extra data at end of input")]
16    ExtraData(Span),
17
18    #[error("Unexpected token {0:?}")]
19    UnexpectedToken(Box<Token>, Span),
20
21    #[error("Unrecognized token at position {0:?}")]
22    UnrecognizedToken(Span),
23
24    #[error("Invalid regex pattern at {0:?}")]
25    InvalidRegex(Span),
26
27    #[error("Unterminated regex pattern at {0:?}")]
28    UnterminatedRegex(Span),
29
30    #[error("Unterminated string literal at {0:?}")]
31    UnterminatedString(Span),
32
33    #[error("Invalid range at {0:?}")]
34    InvalidRange(Span),
35
36    #[error("Invalid hex string at {0:?}")]
37    InvalidHexString(Span),
38
39    #[error("Unterminated hex string at {0:?}")]
40    UnterminatedHexString(Span),
41
42    #[error("Invalid date format at {0:?}")]
43    InvalidDateFormat(Span),
44
45    #[error("Invalid number format at {0:?}")]
46    InvalidNumberFormat(Span),
47
48    #[error("Invalid UR: {0} at {1:?}")]
49    InvalidUr(String, Span),
50
51    #[error("Expected opening parenthesis")]
52    ExpectedOpenParen(Span),
53
54    #[error("Expected closing parenthesis")]
55    ExpectedCloseParen(Span),
56
57    #[error("Expected closing bracket")]
58    ExpectedCloseBracket(Span),
59
60    #[error("Expected closing brace")]
61    ExpectedCloseBrace(Span),
62
63    #[error("Expected colon")]
64    ExpectedColon(Span),
65
66    #[error("Expected pattern after operator")]
67    ExpectedPattern(Span),
68
69    #[error("Unmatched parentheses")]
70    UnmatchedParentheses(Span),
71
72    #[error("Unmatched braces")]
73    UnmatchedBraces(Span),
74
75    #[error("Invalid capture group name")]
76    InvalidCaptureGroupName(String, Span),
77
78    #[error("Invalid digest pattern: {0} at {1:?}")]
79    InvalidDigestPattern(String, Span),
80
81    #[error("Unterminated digest quoted pattern at {0:?}")]
82    UnterminatedDigestQuoted(Span),
83
84    #[error("Unterminated date quoted pattern at {0:?}")]
85    UnterminatedDateQuoted(Span),
86
87    #[error("Unknown error")]
88    #[default]
89    Unknown,
90}
91
92/// A Result type specialized for dCBOR pattern parsing.
93pub type Result<T> = std::result::Result<T, Error>;
94
95impl Error {
96    /// Adjusts the span of an error by adding the given offset to both start
97    /// and end positions. Returns a new error with adjusted span, or the
98    /// original error if it has no span.
99    pub fn adjust_span(self, offset: usize) -> Self {
100        match self {
101            Error::UnrecognizedToken(span) => {
102                Error::UnrecognizedToken(offset + span.start..offset + span.end)
103            }
104            Error::ExtraData(span) => {
105                Error::ExtraData(offset + span.start..offset + span.end)
106            }
107            Error::UnexpectedToken(token, span) => Error::UnexpectedToken(
108                token,
109                offset + span.start..offset + span.end,
110            ),
111            Error::InvalidRegex(span) => {
112                Error::InvalidRegex(offset + span.start..offset + span.end)
113            }
114            Error::UnterminatedRegex(span) => {
115                Error::UnterminatedRegex(offset + span.start..offset + span.end)
116            }
117            Error::UnterminatedString(span) => Error::UnterminatedString(
118                offset + span.start..offset + span.end,
119            ),
120            Error::InvalidRange(span) => {
121                Error::InvalidRange(offset + span.start..offset + span.end)
122            }
123            Error::InvalidHexString(span) => {
124                Error::InvalidHexString(offset + span.start..offset + span.end)
125            }
126            Error::UnterminatedHexString(span) => Error::UnterminatedHexString(
127                offset + span.start..offset + span.end,
128            ),
129            Error::InvalidDateFormat(span) => {
130                Error::InvalidDateFormat(offset + span.start..offset + span.end)
131            }
132            Error::InvalidNumberFormat(span) => Error::InvalidNumberFormat(
133                offset + span.start..offset + span.end,
134            ),
135            Error::InvalidUr(msg, span) => {
136                Error::InvalidUr(msg, offset + span.start..offset + span.end)
137            }
138            Error::ExpectedOpenParen(span) => {
139                Error::ExpectedOpenParen(offset + span.start..offset + span.end)
140            }
141            Error::ExpectedCloseParen(span) => Error::ExpectedCloseParen(
142                offset + span.start..offset + span.end,
143            ),
144            Error::ExpectedCloseBracket(span) => Error::ExpectedCloseBracket(
145                offset + span.start..offset + span.end,
146            ),
147            Error::ExpectedCloseBrace(span) => Error::ExpectedCloseBrace(
148                offset + span.start..offset + span.end,
149            ),
150            Error::ExpectedColon(span) => {
151                Error::ExpectedColon(offset + span.start..offset + span.end)
152            }
153            Error::ExpectedPattern(span) => {
154                Error::ExpectedPattern(offset + span.start..offset + span.end)
155            }
156            Error::UnmatchedParentheses(span) => Error::UnmatchedParentheses(
157                offset + span.start..offset + span.end,
158            ),
159            Error::UnmatchedBraces(span) => {
160                Error::UnmatchedBraces(offset + span.start..offset + span.end)
161            }
162            Error::InvalidCaptureGroupName(name, span) => {
163                Error::InvalidCaptureGroupName(
164                    name,
165                    offset + span.start..offset + span.end,
166                )
167            }
168            Error::InvalidDigestPattern(msg, span) => {
169                Error::InvalidDigestPattern(
170                    msg,
171                    offset + span.start..offset + span.end,
172                )
173            }
174            Error::UnterminatedDigestQuoted(span) => {
175                Error::UnterminatedDigestQuoted(
176                    offset + span.start..offset + span.end,
177                )
178            }
179            Error::UnterminatedDateQuoted(span) => {
180                Error::UnterminatedDateQuoted(
181                    offset + span.start..offset + span.end,
182                )
183            }
184            // For errors without spans, return them as-is
185            _ => self,
186        }
187    }
188}