glint_mask_tools/
error.rs1use std::path::PathBuf;
6use thiserror::Error;
7
8#[derive(Error, Debug)]
10pub enum GlintError {
11 #[error("IO error: {0}")]
12 Io(#[from] std::io::Error),
13
14 #[error("Image processing error: {0}")]
15 Image(#[from] image::ImageError),
16
17 #[error("Configuration error: {message}")]
18 Config { message: String },
19
20 #[error("Sensor error: {message}")]
21 Sensor { message: String },
22
23 #[error("Invalid file format: {path}")]
24 InvalidFormat { path: PathBuf },
25
26 #[error("Missing required files: {files:?}")]
27 MissingFiles { files: Vec<PathBuf> },
28
29 #[error("Invalid threshold value: {value} (must be between 0.0 and 1.0)")]
30 InvalidThreshold { value: f64 },
31
32 #[error("Invalid bit depth: {bit_depth} (supported: 8, 16, 32)")]
33 InvalidBitDepth { bit_depth: u8 },
34
35 #[error("Dimension mismatch: expected {expected:?}, got {actual:?}")]
36 DimensionMismatch {
37 expected: (u32, u32),
38 actual: (u32, u32),
39 },
40
41 #[error("Band count mismatch: expected {expected}, got {actual}")]
42 BandCountMismatch { expected: usize, actual: usize },
43
44 #[error("Processing error: {message}")]
45 Processing { message: String },
46
47 #[error("Validation error: {message}")]
48 Validation { message: String },
49
50 #[error("Serialization error: {0}")]
51 Serialization(#[from] toml::ser::Error),
52
53 #[error("Deserialization error: {0}")]
54 Deserialization(#[from] toml::de::Error),
55
56 #[error("Pattern matching error: {pattern}")]
57 PatternMatch { pattern: String },
58
59 #[error("Concurrency error: {message}")]
60 Concurrency { message: String },
61
62 #[error("Resource exhaustion: {message}")]
63 ResourceExhaustion { message: String },
64}
65
66pub type Result<T> = std::result::Result<T, GlintError>;
68
69impl GlintError {
70 pub fn config(message: impl Into<String>) -> Self {
72 Self::Config {
73 message: message.into(),
74 }
75 }
76
77 pub fn sensor(message: impl Into<String>) -> Self {
79 Self::Sensor {
80 message: message.into(),
81 }
82 }
83
84 pub fn processing(message: impl Into<String>) -> Self {
86 Self::Processing {
87 message: message.into(),
88 }
89 }
90
91 pub fn validation(message: impl Into<String>) -> Self {
93 Self::Validation {
94 message: message.into(),
95 }
96 }
97
98 pub fn concurrency(message: impl Into<String>) -> Self {
100 Self::Concurrency {
101 message: message.into(),
102 }
103 }
104
105 pub fn resource_exhaustion(message: impl Into<String>) -> Self {
107 Self::ResourceExhaustion {
108 message: message.into(),
109 }
110 }
111}
112
113#[cfg(test)]
114mod tests {
115 use super::*;
116
117 #[test]
118 fn test_error_creation() {
119 let error = GlintError::config("test message");
120 assert!(matches!(error, GlintError::Config { .. }));
121 }
122
123 #[test]
124 fn test_error_display() {
125 let error = GlintError::InvalidThreshold { value: 1.5 };
126 let message = error.to_string();
127 assert!(message.contains("1.5"));
128 assert!(message.contains("0.0 and 1.0"));
129 }
130}