use std::sync::Mutex; use server::AppConfig; use server::config::redact_db_url; static ENV_LOCK: Mutex<()> = Mutex::new(()); #[test] fn default_config_binds_loopback() { let config = AppConfig::default(); let addr = config.socket_addr().expect("addr"); assert_eq!(addr.port(), 8080); assert!(addr.ip().is_loopback()); } #[test] fn layered_config_loads_from_workspace() { let _guard = ENV_LOCK.lock().expect("env lock"); let config = AppConfig::load().expect("load config from workspace"); assert_eq!(config.server.host, "127.0.0.1"); assert_eq!(config.frontend.host, "127.0.0.1"); assert!(!config.database.url.is_empty()); } #[test] fn app_double_underscore_overrides_database_url() { let _guard = ENV_LOCK.lock().expect("env lock"); unsafe { std::env::set_var("APP__DATABASE__URL", "postgres://jared:secret@127.0.0.1:5432/mydb"); } let config = AppConfig::load().expect("load config with env override"); unsafe { std::env::remove_var("APP__DATABASE__URL"); } assert_eq!(config.database.url, "postgres://jared:secret@127.0.0.1:5432/mydb"); } #[test] fn redact_db_url_strips_password() { assert_eq!( redact_db_url("postgres://app:hunter2@127.0.0.1:5432/app"), "postgres://app@127.0.0.1:5432/app" ); }