use serde::Deserialize;
use std::fs;
use std::path::Path;
use crate::ConfigFormat;
use crate::ErrorCause;
use crate::HumusConfigError;
use crate::Settings;
pub fn read_from_file<T>(
path: impl AsRef<Path>,
settings: Settings,
) -> Result<(T, ConfigFormat), HumusConfigError>
where
T: for<'de> Deserialize<'de>,
{
let text = match fs::read_to_string(&path) {
Ok(t) => t,
Err(e) => {
return Err(HumusConfigError {
path: path.as_ref().into(),
cause: ErrorCause::FileRead(e),
});
}
};
let path = path.as_ref();
let detected_format = ConfigFormat::guess_from_path(path);
if let Some(detected_format) = detected_format {
if !settings.is_allowed(detected_format) {
return Err(HumusConfigError {
path: path.into(),
cause: ErrorCause::FormatNotAllowed {
format: detected_format,
prefer: settings.prefer,
},
});
}
}
match detected_format.unwrap_or(settings.prefer) {
#[cfg(feature = "json")]
ConfigFormat::Json => match serde_json::from_str(&text) {
Ok(t) => Ok((t, ConfigFormat::Json)),
Err(e) => Err(HumusConfigError {
path: path.into(),
cause: ErrorCause::Json(e),
}),
},
#[cfg(feature = "json5")]
ConfigFormat::Json5 => match json5::from_str(&text) {
Ok(t) => Ok((t, ConfigFormat::Json5)),
Err(e) => Err(HumusConfigError {
path: path.into(),
cause: ErrorCause::Json5(e),
}),
},
#[cfg(feature = "toml")]
ConfigFormat::Toml => match toml::from_str(&text) {
Ok(t) => Ok((t, ConfigFormat::Toml)),
Err(e) => Err(HumusConfigError {
path: path.into(),
cause: ErrorCause::Toml(e),
}),
},
}
}
#[cfg(feature = "json")]
pub fn read_from_json_file<T>(path: impl AsRef<Path>) -> Result<T, HumusConfigError>
where
T: for<'de> Deserialize<'de>,
{
Ok(read_from_file(path, Settings::only_json())?.0)
}
#[cfg(feature = "json5")]
pub fn read_from_json5_file<T>(path: impl AsRef<Path>) -> Result<T, HumusConfigError>
where
T: for<'de> Deserialize<'de>,
{
Ok(read_from_file(path, Settings::only_json5())?.0)
}
#[cfg(feature = "toml")]
pub fn read_from_toml_file<T>(path: impl AsRef<Path>) -> Result<T, HumusConfigError>
where
T: for<'de> Deserialize<'de>,
{
Ok(read_from_file(path, Settings::only_toml())?.0)
}