//! Hand and Trigger registries use std::collections::HashMap; use std::sync::Arc; use tokio::sync::RwLock; use zclaw_types::Result; use super::{Hand, HandConfig, HandContext, HandResult, Trigger, TriggerConfig}; /// Hand registry pub struct HandRegistry { hands: RwLock>>, configs: RwLock>, } impl HandRegistry { pub fn new() -> Self { Self { hands: RwLock::new(HashMap::new()), configs: RwLock::new(HashMap::new()), } } /// Register a hand pub async fn register(&self, hand: Arc) { let config = hand.config().clone(); let mut hands = self.hands.write().await; let mut configs = self.configs.write().await; hands.insert(config.id.clone(), hand); configs.insert(config.id.clone(), config); } /// Get a hand by ID pub async fn get(&self, id: &str) -> Option> { let hands = self.hands.read().await; hands.get(id).cloned() } /// Get hand configuration pub async fn get_config(&self, id: &str) -> Option { let configs = self.configs.read().await; configs.get(id).cloned() } /// List all hands pub async fn list(&self) -> Vec { let configs = self.configs.read().await; configs.values().cloned().collect() } /// Execute a hand pub async fn execute( &self, id: &str, context: &HandContext, input: serde_json::Value, ) -> Result { let hand = self.get(id).await .ok_or_else(|| zclaw_types::ZclawError::NotFound(format!("Hand not found: {}", id)))?; hand.execute(context, input).await } /// Remove a hand pub async fn remove(&self, id: &str) { let mut hands = self.hands.write().await; let mut configs = self.configs.write().await; hands.remove(id); configs.remove(id); } } impl Default for HandRegistry { fn default() -> Self { Self::new() } } /// Trigger registry pub struct TriggerRegistry { triggers: RwLock>>, configs: RwLock>, } impl TriggerRegistry { pub fn new() -> Self { Self { triggers: RwLock::new(HashMap::new()), configs: RwLock::new(HashMap::new()), } } /// Register a trigger pub async fn register(&self, trigger: Arc) { let config = trigger.config().clone(); let mut triggers = self.triggers.write().await; let mut configs = self.configs.write().await; triggers.insert(config.id.clone(), trigger); configs.insert(config.id.clone(), config); } /// Get a trigger by ID pub async fn get(&self, id: &str) -> Option> { let triggers = self.triggers.read().await; triggers.get(id).cloned() } /// List all triggers pub async fn list(&self) -> Vec { let configs = self.configs.read().await; configs.values().cloned().collect() } /// Remove a trigger pub async fn remove(&self, id: &str) { let mut triggers = self.triggers.write().await; let mut configs = self.configs.write().await; triggers.remove(id); configs.remove(id); } } impl Default for TriggerRegistry { fn default() -> Self { Self::new() } }