use std::{
any::{Any, TypeId},
collections::HashMap,
sync::{Arc, RwLock},
};
#[derive(Debug, Default)]
pub struct ClientServiceRegistry {
services: RwLock<HashMap<TypeId, Arc<dyn Any + Send + Sync>>>,
}
impl ClientServiceRegistry {
#[must_use]
pub fn new() -> Self {
Self::default()
}
pub fn register<T: Send + Sync + 'static>(&self, service: Arc<T>) {
let type_id = TypeId::of::<T>();
self.services
.write()
.expect("service registry poisoned")
.insert(type_id, service);
}
#[must_use]
pub fn get<T: Send + Sync + 'static>(&self) -> Option<Arc<T>> {
let type_id = TypeId::of::<T>();
self.services
.read()
.expect("service registry poisoned")
.get(&type_id)
.and_then(|any| any.clone().downcast::<T>().ok())
}
#[must_use]
pub fn contains<T: Send + Sync + 'static>(&self) -> bool {
let type_id = TypeId::of::<T>();
self.services
.read()
.expect("service registry poisoned")
.contains_key(&type_id)
}
#[must_use]
pub fn len(&self) -> usize {
self.services
.read()
.expect("service registry poisoned")
.len()
}
#[must_use]
pub fn is_empty(&self) -> bool {
self.len() == 0
}
}
#[cfg(test)]
#[path = "services_tests.rs"]
mod tests;