use crate::introspection::SettingsIntrospection;
use crate::metadata::{ConfigSchema, SettingGroup, SettingMetadata};
use once_cell::sync::Lazy;
use std::collections::HashMap;
use std::sync::{Arc, RwLock};
#[derive(Debug, Clone, Default)]
pub struct SettingsRegistry {
name: String,
version: String,
settings: HashMap<String, SettingMetadata>,
groups: HashMap<String, SettingGroup>,
}
impl SettingsRegistry {
pub fn new(name: impl Into<String>, version: impl Into<String>) -> Self {
Self {
name: name.into(),
version: version.into(),
settings: HashMap::new(),
groups: HashMap::new(),
}
}
pub fn register(&mut self, metadata: SettingMetadata) {
self.settings.insert(metadata.key.clone(), metadata);
}
pub fn register_many(&mut self, settings: impl IntoIterator<Item = SettingMetadata>) {
for setting in settings {
self.register(setting);
}
}
pub fn register_group(&mut self, group: SettingGroup) {
self.groups.insert(group.name.clone(), group);
}
pub fn metadata(&self, key: &str) -> Option<&SettingMetadata> {
self.settings.get(key)
}
pub fn generate_schema(&self) -> ConfigSchema {
ConfigSchema {
name: self.name.clone(),
version: self.version.clone(),
settings: self.settings.values().cloned().collect(),
groups: self.groups.values().cloned().collect(),
}
}
}
impl SettingsIntrospection for SettingsRegistry {
fn schema(&self) -> ConfigSchema {
self.generate_schema()
}
}
static GLOBAL_REGISTRY: Lazy<Arc<RwLock<SettingsRegistry>>> =
Lazy::new(|| Arc::new(RwLock::new(SettingsRegistry::new("default", "0.1.0"))));
pub fn init_global_registry(name: &str, version: &str) {
let mut registry = GLOBAL_REGISTRY.write().unwrap();
registry.name = name.to_string();
registry.version = version.to_string();
}
pub fn register_setting(metadata: SettingMetadata) {
let mut registry = GLOBAL_REGISTRY.write().unwrap();
registry.register(metadata);
}
pub fn global_schema() -> ConfigSchema {
let registry = GLOBAL_REGISTRY.read().unwrap();
registry.generate_schema()
}