移除 SECRETS_ENV=production 时对 verify-ca/verify-full 的硬性要求, 仍可通过 SECRETS_DATABASE_SSL_MODE 显式选择模式。 Made-with: Cursor
72 lines
2.0 KiB
Rust
72 lines
2.0 KiB
Rust
use std::path::PathBuf;
|
|
|
|
use anyhow::{Context, Result};
|
|
use sqlx::postgres::PgSslMode;
|
|
|
|
#[derive(Debug, Clone)]
|
|
pub struct DatabaseConfig {
|
|
pub url: String,
|
|
pub ssl_mode: Option<PgSslMode>,
|
|
pub ssl_root_cert: Option<PathBuf>,
|
|
}
|
|
|
|
/// Resolve database URL from environment.
|
|
/// Priority: `SECRETS_DATABASE_URL` env var → error.
|
|
pub fn resolve_db_url(override_url: &str) -> Result<String> {
|
|
if !override_url.is_empty() {
|
|
return Ok(override_url.to_string());
|
|
}
|
|
|
|
if let Ok(url) = std::env::var("SECRETS_DATABASE_URL")
|
|
&& !url.is_empty()
|
|
{
|
|
return Ok(url);
|
|
}
|
|
|
|
anyhow::bail!(
|
|
"Database not configured. Set the SECRETS_DATABASE_URL environment variable.\n\
|
|
Example: SECRETS_DATABASE_URL=postgres://user:pass@host:port/dbname"
|
|
)
|
|
}
|
|
|
|
fn env_var_non_empty(name: &str) -> Option<String> {
|
|
std::env::var(name)
|
|
.ok()
|
|
.filter(|value| !value.trim().is_empty())
|
|
}
|
|
|
|
fn parse_ssl_mode_from_env() -> Result<Option<PgSslMode>> {
|
|
let Some(mode) = env_var_non_empty("SECRETS_DATABASE_SSL_MODE") else {
|
|
return Ok(None);
|
|
};
|
|
|
|
let parsed = mode.parse::<PgSslMode>().with_context(|| {
|
|
format!(
|
|
"Invalid SECRETS_DATABASE_SSL_MODE='{mode}'. Use one of: disable, allow, prefer, require, verify-ca, verify-full."
|
|
)
|
|
})?;
|
|
Ok(Some(parsed))
|
|
}
|
|
|
|
fn resolve_ssl_root_cert_from_env() -> Result<Option<PathBuf>> {
|
|
let Some(path) = env_var_non_empty("SECRETS_DATABASE_SSL_ROOT_CERT") else {
|
|
return Ok(None);
|
|
};
|
|
let path = PathBuf::from(path);
|
|
if !path.exists() {
|
|
anyhow::bail!(
|
|
"SECRETS_DATABASE_SSL_ROOT_CERT points to a missing file: {}",
|
|
path.display()
|
|
);
|
|
}
|
|
Ok(Some(path))
|
|
}
|
|
|
|
pub fn resolve_db_config(override_url: &str) -> Result<DatabaseConfig> {
|
|
Ok(DatabaseConfig {
|
|
url: resolve_db_url(override_url)?,
|
|
ssl_mode: parse_ssl_mode_from_env()?,
|
|
ssl_root_cert: resolve_ssl_root_cert_from_env()?,
|
|
})
|
|
}
|