twelve_factor/
configuration.rs1use config::{Config, ConfigError, Environment, File};
2use serde::Deserialize;
3
4pub trait ConfigProvider {
5 fn get_value<'de, T: Deserialize<'de>>(&self, key: &'de str) -> Result<T, ConfigError>;
6}
7
8pub struct ConfigurationPreferences{
9 pub config_file: Option<String>,
10 pub secrets_file: Option<String>,
11 pub prefix: Option<String>,
12 pub separator: Option<String>,
13}
14
15impl Default for ConfigurationPreferences{
16 fn default() -> Self {
17 ConfigurationPreferences{
18 config_file: None,
19 secrets_file: None,
20 prefix: None,
21 separator: None,
22 }
23 }
24}
25
26pub struct Configuration {
27 configuration: Config,
28}
29
30impl Configuration {
31 pub fn read_configuration(prefs: &ConfigurationPreferences) -> Configuration{
32 let paths = match (prefs.config_file.clone(), prefs.secrets_file.clone()) {
33 (Some(config), Some(secrets)) => {
34 vec![File::with_name(&config), File::with_name(&secrets)]
35 }
36 (Some(config), None) => vec![File::with_name(&config)],
37 (None, Some(secrets)) => vec![File::with_name(&secrets)],
38 (None, None) => vec![],
39 };
40
41 let env = match (prefs.prefix.clone(), prefs.separator.clone()){
42 (Some(prefix) , Some(separator)) => {
43 Environment::with_prefix(&prefix).separator(&separator)
44 },
45 (Some(prefix), None) => {
46 Environment::with_prefix(&prefix)
47 },
48 (None, Some(separator)) => {
49 Environment::default().separator(&separator)
50 },
51 (None, None) => {
52 Environment::default()
53 },
54 };
55
56 let mut a_config = Config::new();
57 a_config.merge(paths).unwrap()
58 .merge(env);
59 Configuration{
60 configuration : a_config,
61 }
62 }
63}
64
65impl ConfigProvider for Configuration{
66 fn get_value<'de, T: Deserialize<'de>>(&self, key: &'de str) -> Result<T, ConfigError>{
67 self.configuration.get(key)
68 }
69}
70
71#[cfg(test)]
72mod tests{
73
74}