celestial_coords/
errors.rs1use celestial_core::AstroError;
2use thiserror::Error;
3
4#[cfg(feature = "serde")]
5use serde::{Deserialize, Serialize};
6
7pub type CoordResult<T> = Result<T, CoordError>;
8
9#[derive(Debug, Error)]
10#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
11pub enum CoordError {
12 #[error("Invalid coordinate: {message}")]
13 InvalidCoordinate { message: String },
14
15 #[error("Epoch conversion failed: {source}")]
16 EpochError {
17 #[from]
18 source: celestial_time::TimeError,
19 },
20
21 #[error("Core astronomical calculation failed: {message}")]
22 CoreError { message: String },
23
24 #[error("Invalid distance: {message}")]
25 InvalidDistance { message: String },
26
27 #[error("Observer location required for topocentric coordinates")]
28 MissingObserver,
29
30 #[error("Coordinate operation not supported: {message}")]
31 UnsupportedOperation { message: String },
32
33 #[error("Data parsing failed: {message}")]
34 ParsingError { message: String },
35
36 #[error("Data not available: {message}")]
37 DataUnavailable { message: String },
38
39 #[error("External error: {message}")]
44 ExternalError { message: String },
45}
46
47impl CoordError {
48 pub fn invalid_coordinate(message: impl Into<String>) -> Self {
49 Self::InvalidCoordinate {
50 message: message.into(),
51 }
52 }
53
54 pub fn invalid_distance(message: impl Into<String>) -> Self {
55 Self::InvalidDistance {
56 message: message.into(),
57 }
58 }
59
60 pub fn unsupported_operation(message: impl Into<String>) -> Self {
61 Self::UnsupportedOperation {
62 message: message.into(),
63 }
64 }
65
66 pub fn parsing_error(message: impl Into<String>) -> Self {
67 Self::ParsingError {
68 message: message.into(),
69 }
70 }
71
72 pub fn data_unavailable(message: impl Into<String>) -> Self {
73 Self::DataUnavailable {
74 message: message.into(),
75 }
76 }
77
78 pub fn external_library(operation: &str, error: &str) -> Self {
79 Self::ExternalError {
80 message: format!("{}: {}", operation, error),
81 }
82 }
83
84 pub fn from_core(error: AstroError) -> Self {
85 Self::CoreError {
86 message: error.to_string(),
87 }
88 }
89}
90
91impl From<AstroError> for CoordError {
92 fn from(error: AstroError) -> Self {
93 Self::from_core(error)
94 }
95}
96
97#[cfg(test)]
98mod tests {
99 use super::*;
100
101 #[test]
102 fn test_unsupported_operation() {
103 let err = CoordError::unsupported_operation("test op");
104 assert!(err.to_string().contains("test op"));
105 }
106
107 #[test]
108 fn test_parsing_error() {
109 let err = CoordError::parsing_error("parse fail");
110 assert!(err.to_string().contains("parse fail"));
111 }
112}