1pub type Result<T> = std::result::Result<T, CloudError>;
5
6#[derive(Debug, thiserror::Error)]
8pub enum CloudError {
9 #[error("Storage error: {0}")]
11 Storage(String),
12
13 #[error("Network error: {0}")]
15 Network(String),
16
17 #[error("Authentication error: {0}")]
19 Authentication(String),
20
21 #[error("Authorization error: {0}")]
23 Authorization(String),
24
25 #[error("Object not found: {0}")]
27 NotFound(String),
28
29 #[error("Object already exists: {0}")]
31 AlreadyExists(String),
32
33 #[error("Invalid configuration: {0}")]
35 InvalidConfig(String),
36
37 #[error("Transfer error: {0}")]
39 Transfer(String),
40
41 #[error("Checksum mismatch: expected {expected}, got {actual}")]
43 ChecksumMismatch { expected: String, actual: String },
44
45 #[error("Quota exceeded: {0}")]
47 QuotaExceeded(String),
48
49 #[error("Service unavailable: {0}")]
51 ServiceUnavailable(String),
52
53 #[error("Operation timeout: {0}")]
55 Timeout(String),
56
57 #[error("Serialization error: {0}")]
59 Serialization(String),
60
61 #[error("Media service error: {0}")]
63 MediaService(String),
64
65 #[error("Encryption error: {0}")]
67 Encryption(String),
68
69 #[error("Invalid parameter: {0}")]
71 InvalidParameter(String),
72
73 #[error("Rate limit exceeded: {0}")]
75 RateLimitExceeded(String),
76
77 #[error("Cloud error: {0}")]
79 Other(String),
80}
81
82impl CloudError {
83 #[must_use]
85 pub fn is_retryable(&self) -> bool {
86 matches!(
87 self,
88 CloudError::Network(_)
89 | CloudError::ServiceUnavailable(_)
90 | CloudError::Timeout(_)
91 | CloudError::RateLimitExceeded(_)
92 )
93 }
94
95 #[must_use]
97 pub fn is_client_error(&self) -> bool {
98 matches!(
99 self,
100 CloudError::Authentication(_)
101 | CloudError::Authorization(_)
102 | CloudError::NotFound(_)
103 | CloudError::AlreadyExists(_)
104 | CloudError::InvalidConfig(_)
105 | CloudError::InvalidParameter(_)
106 )
107 }
108
109 #[must_use]
111 pub fn is_server_error(&self) -> bool {
112 matches!(
113 self,
114 CloudError::ServiceUnavailable(_) | CloudError::Storage(_)
115 )
116 }
117}
118
119impl From<reqwest::Error> for CloudError {
121 fn from(err: reqwest::Error) -> Self {
122 if err.is_timeout() {
123 CloudError::Timeout(err.to_string())
124 } else {
125 CloudError::Network(err.to_string())
126 }
127 }
128}
129
130impl From<serde_json::Error> for CloudError {
131 fn from(err: serde_json::Error) -> Self {
132 CloudError::Serialization(err.to_string())
133 }
134}
135
136impl From<std::io::Error> for CloudError {
137 fn from(err: std::io::Error) -> Self {
138 CloudError::Storage(err.to_string())
139 }
140}
141
142impl From<url::ParseError> for CloudError {
143 fn from(err: url::ParseError) -> Self {
144 CloudError::InvalidConfig(err.to_string())
145 }
146}