1use serde::{Deserialize, Serialize};
7use std::collections::HashMap;
8
9pub trait Serializer {
31 type Input;
32 type Output;
33
34 fn serialize(&self, input: &Self::Input) -> Result<Self::Output, SerializerError>;
35 fn deserialize(&self, output: &Self::Output) -> Result<Self::Input, SerializerError>;
36}
37
38#[derive(Debug, Clone, PartialEq, Eq)]
40pub enum ValidatorError {
41 UniqueViolation {
43 field_name: String,
44 value: String,
45 message: String,
46 },
47 UniqueTogetherViolation {
49 field_names: Vec<String>,
50 values: HashMap<String, String>,
51 message: String,
52 },
53 RequiredField { field_name: String, message: String },
55 FieldValidation {
57 field_name: String,
58 value: String,
59 constraint: String,
60 message: String,
61 },
62 DatabaseError {
64 message: String,
65 source: Option<String>,
66 },
67 Custom { message: String },
69}
70
71impl std::fmt::Display for ValidatorError {
72 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
73 match self {
74 ValidatorError::UniqueViolation {
75 field_name,
76 value,
77 message,
78 } => write!(
79 f,
80 "Unique violation on field '{}' with value '{}': {}",
81 field_name, value, message
82 ),
83 ValidatorError::UniqueTogetherViolation {
84 field_names,
85 values,
86 message,
87 } => {
88 let fields_str = format!("[{}]", field_names.join(", "));
90 let mut sorted_values: Vec<_> = values.iter().collect();
93 sorted_values.sort_by_key(|(k, _)| *k);
94 let values_str = sorted_values
95 .into_iter()
96 .map(|(k, v)| format!("{}={}", k, v))
97 .collect::<Vec<_>>()
98 .join(", ");
99 write!(
100 f,
101 "Unique together violation on fields {} with values ({}): {}",
102 fields_str, values_str, message
103 )
104 }
105 ValidatorError::RequiredField {
106 field_name,
107 message,
108 } => write!(f, "Required field '{}': {}", field_name, message),
109 ValidatorError::FieldValidation {
110 field_name,
111 value,
112 constraint,
113 message,
114 } => write!(
115 f,
116 "Field '{}' with value '{}' failed constraint '{}': {}",
117 field_name, value, constraint, message
118 ),
119 ValidatorError::DatabaseError { message, source } => {
120 if let Some(src) = source {
121 write!(f, "Database error: {} (source: {})", message, src)
122 } else {
123 write!(f, "Database error: {}", message)
124 }
125 }
126 ValidatorError::Custom { message } => write!(f, "Validation error: {}", message),
127 }
128 }
129}
130
131impl std::error::Error for ValidatorError {}
132
133impl ValidatorError {
134 pub fn message(&self) -> &str {
136 match self {
137 ValidatorError::UniqueViolation { message, .. } => message,
138 ValidatorError::UniqueTogetherViolation { message, .. } => message,
139 ValidatorError::RequiredField { message, .. } => message,
140 ValidatorError::FieldValidation { message, .. } => message,
141 ValidatorError::DatabaseError { message, .. } => message,
142 ValidatorError::Custom { message } => message,
143 }
144 }
145
146 pub fn field_names(&self) -> Vec<&str> {
148 match self {
149 ValidatorError::UniqueViolation { field_name, .. } => vec![field_name.as_str()],
150 ValidatorError::UniqueTogetherViolation { field_names, .. } => {
151 field_names.iter().map(|s| s.as_str()).collect()
152 }
153 ValidatorError::RequiredField { field_name, .. } => vec![field_name.as_str()],
154 ValidatorError::FieldValidation { field_name, .. } => vec![field_name.as_str()],
155 ValidatorError::DatabaseError { .. } => vec![],
156 ValidatorError::Custom { .. } => vec![],
157 }
158 }
159
160 pub fn is_uniqueness_violation(&self) -> bool {
162 matches!(
163 self,
164 ValidatorError::UniqueViolation { .. } | ValidatorError::UniqueTogetherViolation { .. }
165 )
166 }
167
168 pub fn is_database_error(&self) -> bool {
170 matches!(self, ValidatorError::DatabaseError { .. })
171 }
172}
173
174#[derive(Debug, Clone)]
176pub enum SerializerError {
177 Validation(ValidatorError),
179 Serde { message: String },
181 Other { message: String },
183}
184
185impl std::fmt::Display for SerializerError {
186 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
187 match self {
188 SerializerError::Validation(e) => write!(f, "{}", e),
189 SerializerError::Serde { message } => write!(f, "Serde error: {}", message),
190 SerializerError::Other { message } => write!(f, "Serialization error: {}", message),
191 }
192 }
193}
194
195impl std::error::Error for SerializerError {
196 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
197 match self {
198 SerializerError::Validation(e) => Some(e),
199 _ => None,
200 }
201 }
202}
203
204impl From<ValidatorError> for SerializerError {
205 fn from(err: ValidatorError) -> Self {
206 SerializerError::Validation(err)
207 }
208}
209
210impl SerializerError {
211 pub fn new(message: String) -> Self {
213 SerializerError::Other { message }
214 }
215
216 pub fn validation(error: ValidatorError) -> Self {
218 SerializerError::Validation(error)
219 }
220
221 pub fn unique_violation(field_name: String, value: String, message: String) -> Self {
223 SerializerError::Validation(ValidatorError::UniqueViolation {
224 field_name,
225 value,
226 message,
227 })
228 }
229
230 pub fn unique_together_violation(
232 field_names: Vec<String>,
233 values: HashMap<String, String>,
234 message: String,
235 ) -> Self {
236 SerializerError::Validation(ValidatorError::UniqueTogetherViolation {
237 field_names,
238 values,
239 message,
240 })
241 }
242
243 pub fn required_field(field_name: String, message: String) -> Self {
245 SerializerError::Validation(ValidatorError::RequiredField {
246 field_name,
247 message,
248 })
249 }
250
251 pub fn field_validation(
253 field_name: String,
254 value: String,
255 constraint: String,
256 message: String,
257 ) -> Self {
258 SerializerError::Validation(ValidatorError::FieldValidation {
259 field_name,
260 value,
261 constraint,
262 message,
263 })
264 }
265
266 pub fn database_error(message: String, source: Option<String>) -> Self {
268 SerializerError::Validation(ValidatorError::DatabaseError { message, source })
269 }
270
271 pub fn is_validation_error(&self) -> bool {
273 matches!(self, SerializerError::Validation(_))
274 }
275
276 pub fn message(&self) -> String {
278 match self {
279 SerializerError::Validation(e) => e.message().to_string(),
280 SerializerError::Serde { message } => message.clone(),
281 SerializerError::Other { message } => message.clone(),
282 }
283 }
284
285 pub fn as_validator_error(&self) -> Option<&ValidatorError> {
287 match self {
288 SerializerError::Validation(e) => Some(e),
289 _ => None,
290 }
291 }
292}
293
294pub struct JsonSerializer<T> {
318 _phantom: std::marker::PhantomData<T>,
319}
320
321impl<T> JsonSerializer<T> {
322 pub fn new() -> Self {
324 Self {
325 _phantom: std::marker::PhantomData,
326 }
327 }
328}
329
330impl<T> Default for JsonSerializer<T> {
331 fn default() -> Self {
332 Self::new()
333 }
334}
335
336impl<T> Serializer for JsonSerializer<T>
337where
338 T: Serialize + for<'de> Deserialize<'de>,
339{
340 type Input = T;
341 type Output = String;
342
343 fn serialize(&self, input: &Self::Input) -> Result<Self::Output, SerializerError> {
344 serde_json::to_string(input).map_err(|e| SerializerError::Serde {
345 message: format!("Serialization error: {}", e),
346 })
347 }
348
349 fn deserialize(&self, output: &Self::Output) -> Result<Self::Input, SerializerError> {
350 serde_json::from_str(output).map_err(|e| SerializerError::Serde {
351 message: format!("Deserialization error: {}", e),
352 })
353 }
354}
355
356pub trait Deserializer {
378 type Input;
379 type Output;
380
381 fn deserialize(&self, input: &Self::Input) -> Result<Self::Output, SerializerError>;
382}
383
384#[cfg(test)]
385mod tests {
386 use super::*;
387
388 #[derive(Serialize, Deserialize, PartialEq, Debug)]
389 struct TestUser {
390 id: i64,
391 name: String,
392 }
393
394 #[test]
395 fn test_json_serializer_roundtrip() {
396 let user = TestUser {
397 id: 1,
398 name: "Alice".to_string(),
399 };
400 let serializer = JsonSerializer::<TestUser>::new();
401
402 let json = serializer.serialize(&user).unwrap();
403 let deserialized = serializer.deserialize(&json).unwrap();
404
405 assert_eq!(user.id, deserialized.id);
406 assert_eq!(user.name, deserialized.name);
407 }
408
409 #[test]
410 fn test_json_serializer_serialize() {
411 let user = TestUser {
412 id: 1,
413 name: "Alice".to_string(),
414 };
415 let serializer = JsonSerializer::<TestUser>::new();
416
417 let json = serializer.serialize(&user).unwrap();
418 assert!(json.contains("Alice"));
419 assert!(json.contains("\"id\":1"));
420 }
421
422 #[test]
423 fn test_json_serializer_deserialize() {
424 let json = r#"{"id":1,"name":"Alice"}"#.to_string();
425 let serializer = JsonSerializer::<TestUser>::new();
426
427 let user = serializer.deserialize(&json).unwrap();
428 assert_eq!(user.id, 1);
429 assert_eq!(user.name, "Alice");
430 }
431
432 #[test]
433 fn test_json_serializer_deserialize_error() {
434 let invalid_json = r#"{"invalid"}"#.to_string();
435 let serializer = JsonSerializer::<TestUser>::new();
436
437 let result = serializer.deserialize(&invalid_json);
438 assert!(result.is_err());
439 }
440
441 #[test]
442 fn test_validator_error_display() {
443 let err = ValidatorError::UniqueViolation {
444 field_name: "email".to_string(),
445 value: "test@example.com".to_string(),
446 message: "Email already exists".to_string(),
447 };
448 assert!(err.to_string().contains("email"));
449 assert!(err.to_string().contains("test@example.com"));
450 }
451
452 #[test]
453 fn test_serializer_error_from_validator_error() {
454 let validator_err = ValidatorError::Custom {
455 message: "test error".to_string(),
456 };
457 let serializer_err: SerializerError = validator_err.into();
458
459 match serializer_err {
460 SerializerError::Validation(_) => {}
461 _ => panic!("Expected Validation error"),
462 }
463 }
464}