feat: added file loader

This commit is contained in:
darwincereska
2026-06-08 12:38:41 -04:00
parent 56339890e5
commit 36c74e0c25
8 changed files with 359 additions and 87 deletions
+11
View File
@@ -6,6 +6,9 @@ pub enum EnvError {
/// An environment variable was expected, but it was not found.
MissingVar(String),
/// A file was expected to be found, but it was not found or could not be read.
FileError { path: String, message: String }
}
impl EnvError {
@@ -28,4 +31,12 @@ impl EnvError {
where T: Into<String> {
Self::MissingVar(key.into())
}
/// Creates a new `EnvError::FileMissing` with the given path and message.
pub fn file_error<P: Into<String>, M: Into<String>>(path: P, message: M) -> Self {
Self::FileError {
path: path.into(),
message: message.into()
}
}
}
+29
View File
@@ -49,6 +49,35 @@ impl FromEnv for String {
pub struct EnvLoader;
impl EnvLoader {
/// Creates a new `EnvLoader`.
pub fn new() -> Self {
Self
}
/// Loads environment variables from a file. The file should have one variable per line, in the format `KEY=VALUE`. Lines starting with `#` are treated as comments and ignored.
pub fn load_file(&self, path: &str) -> Result<(), EnvError> {
// Load the file
let contents = std::fs::read_to_string(path).map_err(|e| EnvError::file_error(path, e.to_string()))?;
// Parse the file
for line in contents.lines() {
let line = line.trim();
if line.is_empty() || line.starts_with("#") { continue }
let parts: Vec<&str> = line.splitn(2, '=').collect();
if parts.len() != 2 {
return Err(EnvError::file_error(path, format!("Invalid line: {}", line)));
}
// Trim the key and value
let key = parts[0].trim();
let value = parts[1].trim();
// Set the environment variable
unsafe { std::env::set_var(key, value) }
}
Ok(())
}
/// Creates a new `EnvLoader` with the given prefix.
pub fn with_prefix<P: Into<String>>(&self, prefix: P) -> PrefixedEnvLoader {
PrefixedEnvLoader {