elif_orm/
observers.rs

1use crate::event_error::EventError;
2use crate::events::ModelObserver;
3use std::any::{Any, TypeId};
4use std::collections::HashMap;
5
6pub struct ObserverRegistry<T> {
7    observers: Vec<Box<dyn ModelObserver<T>>>,
8}
9
10impl<T> ObserverRegistry<T> {
11    pub fn new() -> Self {
12        Self {
13            observers: Vec::new(),
14        }
15    }
16
17    pub fn register(&mut self, observer: Box<dyn ModelObserver<T>>) {
18        self.observers.push(observer);
19    }
20
21    pub fn observer_count(&self) -> usize {
22        self.observers.len()
23    }
24
25    pub async fn trigger_creating(&self, model: &mut T) -> Result<(), EventError> {
26        for observer in &self.observers {
27            observer.creating(model).await?;
28        }
29        Ok(())
30    }
31
32    pub async fn trigger_created(&self, model: &T) -> Result<(), EventError> {
33        for observer in &self.observers {
34            observer.created(model).await?;
35        }
36        Ok(())
37    }
38
39    pub async fn trigger_updating(&self, model: &mut T, original: &T) -> Result<(), EventError> {
40        for observer in &self.observers {
41            observer.updating(model, original).await?;
42        }
43        Ok(())
44    }
45
46    pub async fn trigger_updated(&self, model: &T, original: &T) -> Result<(), EventError> {
47        for observer in &self.observers {
48            observer.updated(model, original).await?;
49        }
50        Ok(())
51    }
52
53    pub async fn trigger_saving(&self, model: &mut T) -> Result<(), EventError> {
54        for observer in &self.observers {
55            observer.saving(model).await?;
56        }
57        Ok(())
58    }
59
60    pub async fn trigger_saved(&self, model: &T) -> Result<(), EventError> {
61        for observer in &self.observers {
62            observer.saved(model).await?;
63        }
64        Ok(())
65    }
66
67    pub async fn trigger_deleting(&self, model: &T) -> Result<(), EventError> {
68        for observer in &self.observers {
69            observer.deleting(model).await?;
70        }
71        Ok(())
72    }
73
74    pub async fn trigger_deleted(&self, model: &T) -> Result<(), EventError> {
75        for observer in &self.observers {
76            observer.deleted(model).await?;
77        }
78        Ok(())
79    }
80}
81
82impl<T> Default for ObserverRegistry<T> {
83    fn default() -> Self {
84        Self::new()
85    }
86}
87
88pub struct GlobalObserverRegistry {
89    _observers: Vec<Box<dyn Any + Send + Sync>>,
90}
91
92impl GlobalObserverRegistry {
93    pub fn new() -> Self {
94        Self {
95            _observers: Vec::new(),
96        }
97    }
98
99    pub fn register<T: 'static>(&mut self, _observer: Box<dyn ModelObserver<T> + Send + Sync>) {
100        // For now, simplified global registry - not using Any conversion
101        // This would need a more complex implementation for full functionality
102    }
103
104    pub fn observer_count(&self) -> usize {
105        0 // Simplified for now
106    }
107}
108
109impl Default for GlobalObserverRegistry {
110    fn default() -> Self {
111        Self::new()
112    }
113}
114
115pub struct ObserverManager {
116    model_observers: HashMap<TypeId, Box<dyn Any + Send + Sync>>,
117    global_observers: GlobalObserverRegistry,
118}
119
120impl ObserverManager {
121    pub fn new() -> Self {
122        Self {
123            model_observers: HashMap::new(),
124            global_observers: GlobalObserverRegistry::new(),
125        }
126    }
127
128    pub fn register_for_model<T: 'static>(&mut self, observer: Box<dyn ModelObserver<T>>) {
129        let type_id = TypeId::of::<T>();
130
131        if let Some(registry) = self.model_observers.get_mut(&type_id) {
132            if let Some(registry) = registry.downcast_mut::<ObserverRegistry<T>>() {
133                registry.register(observer);
134                return;
135            }
136        }
137
138        let mut registry = ObserverRegistry::<T>::new();
139        registry.register(observer);
140        self.model_observers.insert(type_id, Box::new(registry));
141    }
142
143    pub fn register_global<T: 'static>(
144        &mut self,
145        observer: Box<dyn ModelObserver<T> + Send + Sync>,
146    ) {
147        self.global_observers.register(observer);
148    }
149
150    pub fn has_observers_for<T: 'static>(&self) -> bool {
151        let type_id = TypeId::of::<T>();
152        self.model_observers.contains_key(&type_id)
153    }
154
155    pub fn global_observer_count(&self) -> usize {
156        self.global_observers.observer_count()
157    }
158
159    pub fn get_registry_for<T: 'static>(&self) -> Option<&ObserverRegistry<T>> {
160        let type_id = TypeId::of::<T>();
161        self.model_observers
162            .get(&type_id)?
163            .downcast_ref::<ObserverRegistry<T>>()
164    }
165
166    pub fn get_registry_for_mut<T: 'static>(&mut self) -> Option<&mut ObserverRegistry<T>> {
167        let type_id = TypeId::of::<T>();
168        self.model_observers
169            .get_mut(&type_id)?
170            .downcast_mut::<ObserverRegistry<T>>()
171    }
172}
173
174impl Default for ObserverManager {
175    fn default() -> Self {
176        Self::new()
177    }
178}
179
180#[cfg(test)]
181mod tests {
182    use super::*;
183    use async_trait::async_trait;
184    use std::sync::{Arc, Mutex};
185
186    #[derive(Debug, Clone, PartialEq)]
187    struct TestUser {
188        id: i64,
189        name: String,
190        email: String,
191    }
192
193    impl Default for TestUser {
194        fn default() -> Self {
195            Self {
196                id: 1,
197                name: "Test User".to_string(),
198                email: "test@example.com".to_string(),
199            }
200        }
201    }
202
203    #[derive(Debug, Clone)]
204    struct EventTracker {
205        events: Arc<Mutex<Vec<String>>>,
206    }
207
208    impl EventTracker {
209        fn new() -> Self {
210            Self {
211                events: Arc::new(Mutex::new(Vec::new())),
212            }
213        }
214
215        fn track(&self, event: &str) {
216            self.events.lock().unwrap().push(event.to_string());
217        }
218
219        fn get_events(&self) -> Vec<String> {
220            self.events.lock().unwrap().clone()
221        }
222
223        #[allow(dead_code)]
224        fn clear(&self) {
225            self.events.lock().unwrap().clear();
226        }
227    }
228
229    #[derive(Clone)]
230    struct TrackingObserver {
231        tracker: EventTracker,
232        name: String,
233    }
234
235    impl TrackingObserver {
236        fn new(name: &str, tracker: EventTracker) -> Self {
237            Self {
238                tracker,
239                name: name.to_string(),
240            }
241        }
242    }
243
244    #[async_trait]
245    impl ModelObserver<TestUser> for TrackingObserver {
246        async fn creating(&self, model: &mut TestUser) -> Result<(), EventError> {
247            self.tracker
248                .track(&format!("{}: creating {}", self.name, model.name));
249            Ok(())
250        }
251
252        async fn created(&self, model: &TestUser) -> Result<(), EventError> {
253            self.tracker
254                .track(&format!("{}: created {}", self.name, model.name));
255            Ok(())
256        }
257    }
258
259    #[tokio::test]
260    async fn test_observer_registry_creation() {
261        let registry = ObserverRegistry::<TestUser>::new();
262        assert_eq!(registry.observer_count(), 0);
263    }
264
265    #[tokio::test]
266    async fn test_observer_registry_register() {
267        let mut registry = ObserverRegistry::<TestUser>::new();
268        let tracker = EventTracker::new();
269        let observer = TrackingObserver::new("observer1", tracker.clone());
270
271        registry.register(Box::new(observer));
272        assert_eq!(registry.observer_count(), 1);
273    }
274
275    #[tokio::test]
276    async fn test_observer_registry_multiple_observers() {
277        let mut registry = ObserverRegistry::<TestUser>::new();
278        let tracker = EventTracker::new();
279
280        let observer1 = TrackingObserver::new("observer1", tracker.clone());
281        let observer2 = TrackingObserver::new("observer2", tracker.clone());
282
283        registry.register(Box::new(observer1));
284        registry.register(Box::new(observer2));
285
286        assert_eq!(registry.observer_count(), 2);
287    }
288
289    #[tokio::test]
290    async fn test_observer_registry_trigger_creating() {
291        let mut registry = ObserverRegistry::<TestUser>::new();
292        let tracker = EventTracker::new();
293        let observer = TrackingObserver::new("observer1", tracker.clone());
294
295        registry.register(Box::new(observer));
296
297        let mut user = TestUser::default();
298        let result = registry.trigger_creating(&mut user).await;
299
300        assert!(result.is_ok());
301
302        let events = tracker.get_events();
303        assert_eq!(events.len(), 1);
304        assert_eq!(events[0], "observer1: creating Test User");
305    }
306
307    #[tokio::test]
308    async fn test_observer_registry_trigger_created() {
309        let mut registry = ObserverRegistry::<TestUser>::new();
310        let tracker = EventTracker::new();
311        let observer = TrackingObserver::new("observer1", tracker.clone());
312
313        registry.register(Box::new(observer));
314
315        let user = TestUser::default();
316        let result = registry.trigger_created(&user).await;
317
318        assert!(result.is_ok());
319
320        let events = tracker.get_events();
321        assert_eq!(events.len(), 1);
322        assert_eq!(events[0], "observer1: created Test User");
323    }
324
325    #[tokio::test]
326    async fn test_observer_registry_multiple_observers_execution_order() {
327        let mut registry = ObserverRegistry::<TestUser>::new();
328        let tracker = EventTracker::new();
329
330        let observer1 = TrackingObserver::new("observer1", tracker.clone());
331        let observer2 = TrackingObserver::new("observer2", tracker.clone());
332
333        registry.register(Box::new(observer1));
334        registry.register(Box::new(observer2));
335
336        let mut user = TestUser::default();
337        let result = registry.trigger_creating(&mut user).await;
338
339        assert!(result.is_ok());
340
341        let events = tracker.get_events();
342        assert_eq!(events.len(), 2);
343        assert_eq!(events[0], "observer1: creating Test User");
344        assert_eq!(events[1], "observer2: creating Test User");
345    }
346
347    #[tokio::test]
348    async fn test_observer_registry_error_handling() {
349        struct FailingObserver;
350
351        #[async_trait]
352        impl ModelObserver<TestUser> for FailingObserver {
353            async fn creating(&self, _model: &mut TestUser) -> Result<(), EventError> {
354                Err(EventError::validation("Observer failed"))
355            }
356        }
357
358        let mut registry = ObserverRegistry::<TestUser>::new();
359        registry.register(Box::new(FailingObserver));
360
361        let mut user = TestUser::default();
362        let result = registry.trigger_creating(&mut user).await;
363
364        assert!(result.is_err());
365        match result.unwrap_err() {
366            EventError::Validation { message, .. } => {
367                assert_eq!(message, "Observer failed");
368            }
369            _ => panic!("Expected validation error"),
370        }
371    }
372
373    #[tokio::test]
374    async fn test_observer_registry_error_propagation_stops_execution() {
375        let mut registry = ObserverRegistry::<TestUser>::new();
376        let tracker = EventTracker::new();
377
378        // First observer that fails
379        struct FailingObserver;
380        #[async_trait]
381        impl ModelObserver<TestUser> for FailingObserver {
382            async fn creating(&self, _model: &mut TestUser) -> Result<(), EventError> {
383                Err(EventError::validation("First observer failed"))
384            }
385        }
386
387        // Second observer that should not be executed
388        let observer2 = TrackingObserver::new("observer2", tracker.clone());
389
390        registry.register(Box::new(FailingObserver));
391        registry.register(Box::new(observer2));
392
393        let mut user = TestUser::default();
394        let result = registry.trigger_creating(&mut user).await;
395
396        assert!(result.is_err());
397
398        // Second observer should not have been called
399        let events = tracker.get_events();
400        assert_eq!(events.len(), 0);
401    }
402
403    #[tokio::test]
404    async fn test_global_observer_registry() {
405        let mut global_registry = GlobalObserverRegistry::new();
406        assert_eq!(global_registry.observer_count(), 0);
407
408        let tracker = EventTracker::new();
409        let observer = TrackingObserver::new("global", tracker.clone());
410
411        global_registry.register(Box::new(observer));
412        // Simplified implementation returns 0 for now
413        assert_eq!(global_registry.observer_count(), 0);
414    }
415
416    #[tokio::test]
417    async fn test_observer_manager_creation() {
418        let manager = ObserverManager::new();
419
420        // Should have no model-specific observers initially
421        assert!(!manager.has_observers_for::<TestUser>());
422    }
423
424    #[tokio::test]
425    async fn test_observer_manager_register_model_observer() {
426        let mut manager = ObserverManager::new();
427        let tracker = EventTracker::new();
428        let observer = TrackingObserver::new("model_observer", tracker.clone());
429
430        manager.register_for_model::<TestUser>(Box::new(observer));
431
432        assert!(manager.has_observers_for::<TestUser>());
433    }
434
435    #[tokio::test]
436    async fn test_observer_manager_register_global_observer() {
437        let mut manager = ObserverManager::new();
438        let tracker = EventTracker::new();
439        let observer = TrackingObserver::new("global_observer", tracker.clone());
440
441        manager.register_global(Box::new(observer));
442
443        // Global observers should be accessible (simplified implementation returns 0)
444        assert_eq!(manager.global_observer_count(), 0);
445    }
446}