elif_orm/
events.rs

1use crate::event_error::EventError;
2use async_trait::async_trait;
3
4#[derive(Debug, Clone)]
5pub enum ModelEvent<T> {
6    Creating(T),
7    Created(T),
8    Updating(T, T), // (old, new)
9    Updated(T, T),
10    Saving(T),
11    Saved(T),
12    Deleting(T),
13    Deleted(T),
14}
15
16#[async_trait]
17pub trait ModelObserver<T>: Send + Sync {
18    async fn creating(&self, _model: &mut T) -> Result<(), EventError> {
19        Ok(())
20    }
21
22    async fn created(&self, _model: &T) -> Result<(), EventError> {
23        Ok(())
24    }
25
26    async fn updating(&self, _model: &mut T, _original: &T) -> Result<(), EventError> {
27        Ok(())
28    }
29
30    async fn updated(&self, _model: &T, _original: &T) -> Result<(), EventError> {
31        Ok(())
32    }
33
34    async fn saving(&self, _model: &mut T) -> Result<(), EventError> {
35        Ok(())
36    }
37
38    async fn saved(&self, _model: &T) -> Result<(), EventError> {
39        Ok(())
40    }
41
42    async fn deleting(&self, _model: &T) -> Result<(), EventError> {
43        Ok(())
44    }
45
46    async fn deleted(&self, _model: &T) -> Result<(), EventError> {
47        Ok(())
48    }
49}
50
51#[cfg(test)]
52mod tests {
53    use super::*;
54    use std::sync::{Arc, Mutex};
55
56    #[derive(Debug, Clone, PartialEq)]
57    struct TestUser {
58        id: i64,
59        name: String,
60        email: String,
61    }
62
63    impl Default for TestUser {
64        fn default() -> Self {
65            Self {
66                id: 1,
67                name: "Test User".to_string(),
68                email: "test@example.com".to_string(),
69            }
70        }
71    }
72
73    #[derive(Debug, Clone)]
74    struct TestObserver {
75        events: Arc<Mutex<Vec<String>>>,
76    }
77
78    impl TestObserver {
79        fn new() -> Self {
80            Self {
81                events: Arc::new(Mutex::new(Vec::new())),
82            }
83        }
84
85        fn get_events(&self) -> Vec<String> {
86            self.events.lock().unwrap().clone()
87        }
88    }
89
90    #[async_trait]
91    impl ModelObserver<TestUser> for TestObserver {
92        async fn creating(&self, model: &mut TestUser) -> Result<(), EventError> {
93            self.events
94                .lock()
95                .unwrap()
96                .push(format!("creating: {}", model.name));
97            Ok(())
98        }
99
100        async fn created(&self, model: &TestUser) -> Result<(), EventError> {
101            self.events
102                .lock()
103                .unwrap()
104                .push(format!("created: {}", model.name));
105            Ok(())
106        }
107
108        async fn updating(
109            &self,
110            model: &mut TestUser,
111            original: &TestUser,
112        ) -> Result<(), EventError> {
113            self.events
114                .lock()
115                .unwrap()
116                .push(format!("updating: {} -> {}", original.name, model.name));
117            Ok(())
118        }
119
120        async fn updated(&self, model: &TestUser, original: &TestUser) -> Result<(), EventError> {
121            self.events
122                .lock()
123                .unwrap()
124                .push(format!("updated: {} -> {}", original.name, model.name));
125            Ok(())
126        }
127
128        async fn saving(&self, model: &mut TestUser) -> Result<(), EventError> {
129            self.events
130                .lock()
131                .unwrap()
132                .push(format!("saving: {}", model.name));
133            Ok(())
134        }
135
136        async fn saved(&self, model: &TestUser) -> Result<(), EventError> {
137            self.events
138                .lock()
139                .unwrap()
140                .push(format!("saved: {}", model.name));
141            Ok(())
142        }
143
144        async fn deleting(&self, model: &TestUser) -> Result<(), EventError> {
145            self.events
146                .lock()
147                .unwrap()
148                .push(format!("deleting: {}", model.name));
149            Ok(())
150        }
151
152        async fn deleted(&self, model: &TestUser) -> Result<(), EventError> {
153            self.events
154                .lock()
155                .unwrap()
156                .push(format!("deleted: {}", model.name));
157            Ok(())
158        }
159    }
160
161    #[tokio::test]
162    async fn test_model_event_enum_creation() {
163        let user = TestUser::default();
164        let event = ModelEvent::Creating(user.clone());
165
166        match event {
167            ModelEvent::Creating(model) => {
168                assert_eq!(model.name, "Test User");
169                assert_eq!(model.email, "test@example.com");
170            }
171            _ => panic!("Expected Creating event"),
172        }
173    }
174
175    #[tokio::test]
176    async fn test_observer_creating_event() {
177        let observer = TestObserver::new();
178        let mut user = TestUser::default();
179
180        let result = observer.creating(&mut user).await;
181        assert!(result.is_ok());
182
183        let events = observer.get_events();
184        assert_eq!(events.len(), 1);
185        assert_eq!(events[0], "creating: Test User");
186    }
187
188    #[tokio::test]
189    async fn test_observer_created_event() {
190        let observer = TestObserver::new();
191        let user = TestUser::default();
192
193        let result = observer.created(&user).await;
194        assert!(result.is_ok());
195
196        let events = observer.get_events();
197        assert_eq!(events.len(), 1);
198        assert_eq!(events[0], "created: Test User");
199    }
200
201    #[tokio::test]
202    async fn test_observer_updating_event() {
203        let observer = TestObserver::new();
204        let original = TestUser::default();
205        let mut updated = TestUser {
206            name: "Updated User".to_string(),
207            ..original.clone()
208        };
209
210        let result = observer.updating(&mut updated, &original).await;
211        assert!(result.is_ok());
212
213        let events = observer.get_events();
214        assert_eq!(events.len(), 1);
215        assert_eq!(events[0], "updating: Test User -> Updated User");
216    }
217
218    #[tokio::test]
219    async fn test_observer_updated_event() {
220        let observer = TestObserver::new();
221        let original = TestUser::default();
222        let updated = TestUser {
223            name: "Updated User".to_string(),
224            ..original.clone()
225        };
226
227        let result = observer.updated(&updated, &original).await;
228        assert!(result.is_ok());
229
230        let events = observer.get_events();
231        assert_eq!(events.len(), 1);
232        assert_eq!(events[0], "updated: Test User -> Updated User");
233    }
234
235    #[tokio::test]
236    async fn test_observer_saving_event() {
237        let observer = TestObserver::new();
238        let mut user = TestUser::default();
239
240        let result = observer.saving(&mut user).await;
241        assert!(result.is_ok());
242
243        let events = observer.get_events();
244        assert_eq!(events.len(), 1);
245        assert_eq!(events[0], "saving: Test User");
246    }
247
248    #[tokio::test]
249    async fn test_observer_saved_event() {
250        let observer = TestObserver::new();
251        let user = TestUser::default();
252
253        let result = observer.saved(&user).await;
254        assert!(result.is_ok());
255
256        let events = observer.get_events();
257        assert_eq!(events.len(), 1);
258        assert_eq!(events[0], "saved: Test User");
259    }
260
261    #[tokio::test]
262    async fn test_observer_deleting_event() {
263        let observer = TestObserver::new();
264        let user = TestUser::default();
265
266        let result = observer.deleting(&user).await;
267        assert!(result.is_ok());
268
269        let events = observer.get_events();
270        assert_eq!(events.len(), 1);
271        assert_eq!(events[0], "deleting: Test User");
272    }
273
274    #[tokio::test]
275    async fn test_observer_deleted_event() {
276        let observer = TestObserver::new();
277        let user = TestUser::default();
278
279        let result = observer.deleted(&user).await;
280        assert!(result.is_ok());
281
282        let events = observer.get_events();
283        assert_eq!(events.len(), 1);
284        assert_eq!(events[0], "deleted: Test User");
285    }
286
287    #[tokio::test]
288    async fn test_event_error_creation() {
289        let error = EventError::validation("Test validation error");
290
291        match error {
292            EventError::Validation { message, .. } => {
293                assert_eq!(message, "Test validation error");
294            }
295            _ => panic!("Expected validation error"),
296        }
297    }
298
299    #[tokio::test]
300    async fn test_observer_error_handling() {
301        struct FailingObserver;
302
303        #[async_trait]
304        impl ModelObserver<TestUser> for FailingObserver {
305            async fn creating(&self, _model: &mut TestUser) -> Result<(), EventError> {
306                Err(EventError::validation("Email already exists"))
307            }
308        }
309
310        let observer = FailingObserver;
311        let mut user = TestUser::default();
312
313        let result = observer.creating(&mut user).await;
314        assert!(result.is_err());
315
316        match result.unwrap_err() {
317            EventError::Validation { message, .. } => {
318                assert_eq!(message, "Email already exists");
319            }
320            _ => panic!("Expected validation error"),
321        }
322    }
323}