verdure_core/error/
component.rs1use crate::error::container::{ContainerError, ContainerErrorKind};
7use std::fmt;
8
9#[derive(Debug)]
23pub enum ComponentError {
24 DependencyNotFound(String),
26 DowncastFailed(String),
28 CircularDependency(String),
30 ConfigurationError(String),
32 CreationError(String),
34 NotFound(String),
36}
37
38impl fmt::Display for ComponentError {
39 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
40 match self {
41 ComponentError::DependencyNotFound(s) => write!(f, "Dependency '{}' not found", s),
42 ComponentError::DowncastFailed(s) => write!(f, "Failed to downcast dependency '{}'", s),
43 ComponentError::CircularDependency(s) => {
44 write!(f, "Circular dependency detected: {}", s)
45 }
46 ComponentError::ConfigurationError(s) => write!(f, "Configuration error: {}", s),
47 ComponentError::CreationError(s) => write!(f, "Component creation error: {}", s),
48 ComponentError::NotFound(s) => write!(f, "Component not found: {}", s),
49 }
50 }
51}
52
53impl From<ContainerError> for ComponentError {
54 fn from(err: ContainerError) -> Self {
55 match err.kind {
56 ContainerErrorKind::NotFound => ComponentError::NotFound(err.message),
57 ContainerErrorKind::CircularDependency => {
58 ComponentError::CircularDependency(err.message)
59 }
60 ContainerErrorKind::CreationFailed => ComponentError::CreationError(err.message),
61 ContainerErrorKind::TypeCastFailed => ComponentError::DowncastFailed(err.message),
62 ContainerErrorKind::Configuration => ComponentError::ConfigurationError(err.message),
63 ContainerErrorKind::Other => ComponentError::CreationError(err.message),
64 }
65 }
66}
67
68impl From<ComponentError> for ContainerError {
69 fn from(err: ComponentError) -> Self {
70 match err {
71 ComponentError::NotFound(msg) => ContainerError::not_found(msg),
72 ComponentError::CircularDependency(msg) => ContainerError::circular_dependency(msg),
73 ComponentError::CreationError(msg) => ContainerError::creation_failed(msg),
74 ComponentError::DowncastFailed(msg) => ContainerError::type_cast_failed(msg),
75 ComponentError::ConfigurationError(msg) => ContainerError::configuration(msg),
76 ComponentError::DependencyNotFound(msg) => {
77 ContainerError::not_found(format!("Dependency: {}", msg))
78 }
79 }
80 }
81}
82
83#[cfg(test)]
84mod tests {
85 use super::*;
86
87 #[test]
88 fn test_component_error_display() {
89 let errors = vec![
90 ComponentError::DependencyNotFound("TestDep".to_string()),
91 ComponentError::DowncastFailed("TestComponent".to_string()),
92 ComponentError::CircularDependency("A -> B -> A".to_string()),
93 ComponentError::ConfigurationError("Invalid config".to_string()),
94 ComponentError::CreationError("Failed to create".to_string()),
95 ComponentError::NotFound("ComponentX".to_string()),
96 ];
97
98 let expected_messages = vec![
99 "Dependency 'TestDep' not found",
100 "Failed to downcast dependency 'TestComponent'",
101 "Circular dependency detected: A -> B -> A",
102 "Configuration error: Invalid config",
103 "Component creation error: Failed to create",
104 "Component not found: ComponentX",
105 ];
106
107 for (error, expected) in errors.iter().zip(expected_messages.iter()) {
108 assert_eq!(error.to_string(), *expected);
109 }
110 }
111
112 #[test]
113 fn test_from_container_error() {
114 let container_errors = vec![
115 ContainerError::not_found("test component"),
116 ContainerError::circular_dependency("A -> B -> A"),
117 ContainerError::creation_failed("creation failed"),
118 ContainerError::type_cast_failed("cast failed"),
119 ContainerError::configuration("config error"),
120 ContainerError::other("other error"),
121 ];
122
123 let component_errors: Vec<ComponentError> = container_errors
124 .into_iter()
125 .map(ComponentError::from)
126 .collect();
127
128 assert!(matches!(component_errors[0], ComponentError::NotFound(_)));
129 assert!(matches!(
130 component_errors[1],
131 ComponentError::CircularDependency(_)
132 ));
133 assert!(matches!(
134 component_errors[2],
135 ComponentError::CreationError(_)
136 ));
137 assert!(matches!(
138 component_errors[3],
139 ComponentError::DowncastFailed(_)
140 ));
141 assert!(matches!(
142 component_errors[4],
143 ComponentError::ConfigurationError(_)
144 ));
145 assert!(matches!(
146 component_errors[5],
147 ComponentError::CreationError(_)
148 ));
149 }
150
151 #[test]
152 fn test_to_container_error() {
153 let component_errors = vec![
154 ComponentError::NotFound("test".to_string()),
155 ComponentError::CircularDependency("A -> B -> A".to_string()),
156 ComponentError::CreationError("create failed".to_string()),
157 ComponentError::DowncastFailed("cast failed".to_string()),
158 ComponentError::ConfigurationError("config error".to_string()),
159 ComponentError::DependencyNotFound("dependency".to_string()),
160 ];
161
162 let container_errors: Vec<ContainerError> = component_errors
163 .into_iter()
164 .map(ContainerError::from)
165 .collect();
166
167 assert_eq!(container_errors[0].kind, ContainerErrorKind::NotFound);
168 assert_eq!(
169 container_errors[1].kind,
170 ContainerErrorKind::CircularDependency
171 );
172 assert_eq!(container_errors[2].kind, ContainerErrorKind::CreationFailed);
173 assert_eq!(container_errors[3].kind, ContainerErrorKind::TypeCastFailed);
174 assert_eq!(container_errors[4].kind, ContainerErrorKind::Configuration);
175 assert_eq!(container_errors[5].kind, ContainerErrorKind::NotFound);
176 assert!(
177 container_errors[5]
178 .message
179 .contains("Dependency: dependency")
180 );
181 }
182
183 #[test]
184 fn test_error_roundup_conversion() {
185 let original_container_error = ContainerError::circular_dependency("A -> B -> A");
186 let component_error: ComponentError = original_container_error.into();
187 let back_to_container: ContainerError = component_error.into();
188
189 assert_eq!(
190 back_to_container.kind,
191 ContainerErrorKind::CircularDependency
192 );
193 assert_eq!(back_to_container.message, "A -> B -> A");
194 }
195}