qubit_text_codec/error/charset_decode_error_kind.rs
1/*******************************************************************************
2 *
3 * Copyright (c) 2026 Haixing Hu.
4 *
5 * SPDX-License-Identifier: Apache-2.0
6 *
7 * Licensed under the Apache License, Version 2.0.
8 *
9 ******************************************************************************/
10use thiserror::Error;
11
12/// Classifies failures detected while decoding encoded units into Unicode text.
13#[derive(Clone, Copy, Debug, Eq, Error, PartialEq)]
14pub enum CharsetDecodeErrorKind {
15 /// The input units do not form a well-formed encoded sequence.
16 #[error("The encoded text sequence is malformed.")]
17 MalformedSequence {
18 /// Optional malformed raw value captured from the offending input unit.
19 value: Option<u32>,
20 },
21
22 /// The closed input ended before a complete character was available.
23 #[error("The encoded text sequence is incomplete (required {required} units, available {available} units).")]
24 IncompleteSequence {
25 /// Total units required to complete the current sequence.
26 required: usize,
27
28 /// Total units currently available from the start of the current sequence.
29 available: usize,
30 },
31
32 /// The decoded numeric value is not a valid Unicode scalar value.
33 #[error("The decoded code point 0x{value:x} is not a valid Unicode scalar value.")]
34 InvalidCodePoint {
35 /// Raw decoded code-point value.
36 value: u32,
37 },
38}
39
40impl CharsetDecodeErrorKind {
41 /// Returns the number of required input units for this kind, if available.
42 ///
43 /// # Returns
44 ///
45 /// - `Some(required)` for [`Self::IncompleteSequence`];
46 /// - `None` for all other variants.
47 #[must_use]
48 #[inline]
49 pub const fn required(self) -> Option<usize> {
50 match self {
51 Self::IncompleteSequence { required, .. } => Some(required),
52 Self::MalformedSequence { .. } | Self::InvalidCodePoint { .. } => None,
53 }
54 }
55
56 /// Returns the number of currently available input units for this kind, if
57 /// available.
58 ///
59 /// # Returns
60 ///
61 /// - `Some(available)` for [`Self::IncompleteSequence`];
62 /// - `None` for all other variants.
63 #[must_use]
64 #[inline]
65 pub const fn available(self) -> Option<usize> {
66 match self {
67 Self::IncompleteSequence { available, .. } => Some(available),
68 Self::MalformedSequence { .. } | Self::InvalidCodePoint { .. } => None,
69 }
70 }
71
72 /// Returns the raw malformed value associated with this decoding error, if any.
73 ///
74 /// # Returns
75 ///
76 /// - `Some(value)` for [`Self::MalformedSequence`] when a specific malformed
77 /// unit value is available.
78 /// - `Some(value)` for [`Self::InvalidCodePoint`].
79 /// - `None` for other variants.
80 #[must_use]
81 #[inline]
82 pub const fn value(self) -> Option<u32> {
83 match self {
84 Self::MalformedSequence { value } => value,
85 Self::InvalidCodePoint { value } => Some(value),
86 Self::IncompleteSequence { .. } => None,
87 }
88 }
89}