use tracing::info;
use crate::error::ServerError;
use super::load::LoadedConfig;
use super::{CliOverrides, ConfigSource, ServerConfig, file};
pub const FIRST_RUN_CONFIG: &str = include_str!("../../templates/first-run-config.toml");
#[cfg(unix)]
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub(crate) enum ScaffoldOutcome {
Written,
AlreadyPresent,
}
pub(crate) fn load_or_scaffold(cli: &CliOverrides) -> Result<LoadedConfig, ServerError> {
let loaded = ServerConfig::load_resolved(cli)?;
if !matches!(loaded.resolution.source, ConfigSource::BuiltInDefaults) {
return Ok(loaded);
}
scaffold_and_reload(cli, loaded)
}
#[cfg(unix)]
fn scaffold_and_reload(
cli: &CliOverrides,
loaded: LoadedConfig,
) -> Result<LoadedConfig, ServerError> {
let home = loaded.resolution.home;
let path = home.join(file::HOME_CONFIG_FILE);
match scaffold_home_config(&home)? {
ScaffoldOutcome::Written => info!(
path = %path.display(),
"no server config found at any discovery layer; scaffolded a first-run config"
),
ScaffoldOutcome::AlreadyPresent => info!(
path = %path.display(),
"a server config appeared after discovery ran; leaving it untouched and using it"
),
}
ServerConfig::load_resolved(cli)
}
#[cfg(not(unix))]
fn scaffold_and_reload(
_cli: &CliOverrides,
loaded: LoadedConfig,
) -> Result<LoadedConfig, ServerError> {
Ok(loaded)
}
#[cfg(unix)]
pub(crate) fn scaffold_home_config(home: &std::path::Path) -> Result<ScaffoldOutcome, ServerError> {
let dir = crate::filesystem::ConfinedDir::open_or_create(home).map_err(|error| {
ServerError::Config {
message: format!("unsafe Aion home `{}`: {error}", home.display()),
}
})?;
match dir.create_new(
std::path::Path::new(file::HOME_CONFIG_FILE),
FIRST_RUN_CONFIG.as_bytes(),
) {
Ok(()) => Ok(ScaffoldOutcome::Written),
Err(error) if error.kind() == std::io::ErrorKind::AlreadyExists => {
Ok(ScaffoldOutcome::AlreadyPresent)
}
Err(error) => Err(ServerError::Config {
message: format!(
"failed to scaffold first-run config `{}`: {error}",
home.join(file::HOME_CONFIG_FILE).display()
),
}),
}
}
#[cfg(test)]
#[path = "scaffold_tests.rs"]
mod tests;