ForgeFlux/src/settings/database.rs

74 lines
1.9 KiB
Rust

use std::env;
use config::{builder::DefaultState, ConfigBuilder, ConfigError};
use derive_more::Display;
use serde::{Deserialize, Serialize};
use url::Url;
#[derive(Deserialize, Serialize, Display, Eq, PartialEq, Clone, Debug)]
#[serde(rename_all = "lowercase")]
pub enum DBType {
#[display(fmt = "postgres")]
Postgres,
}
impl DBType {
fn from_url(url: &Url) -> Result<Self, ConfigError> {
match url.scheme() {
// "mysql" => Ok(Self::Maria),
"postgres" => Ok(Self::Postgres),
_ => Err(ConfigError::Message("Unknown database type".into())),
}
}
}
#[derive(Debug, Clone, Deserialize, Eq, PartialEq)]
pub struct Database {
pub url: String,
pub pool: u32,
pub database_type: DBType,
}
impl Database {
pub fn env_override(mut s: ConfigBuilder<DefaultState>) -> ConfigBuilder<DefaultState> {
for (parameter, env_var_name) in [
("database.url", "DATABASE_URL"),
("database.pool", "FORGEFLUX_database_POOL"),
]
.iter()
{
if let Ok(val) = env::var(env_var_name) {
log::debug!("Overriding [{parameter}] with environment variable {env_var_name}");
s = s.set_override(parameter, val).unwrap();
}
}
s
}
pub fn set_database_type(&mut self) {
let url =
Url::parse(&self.url).expect("couldn't parse Database URL and detect database type");
self.database_type = DBType::from_url(&url).unwrap();
}
}
#[cfg(test)]
mod tests {
use crate::env_helper;
use super::*;
#[test]
fn test_db_env_override() {
let init_settings = crate::settings::Settings::new().unwrap();
env_helper!(
init_settings,
"DATABASE_URL",
"postgres://test_db_env_override",
database.url
);
env_helper!(init_settings, "FORGEFLUX_database_POOL", 99, database.pool);
}
}