mirror of
https://github.com/coastalwhite/lemurs
synced 2024-11-22 01:53:03 +00:00
moved error handling back to main
This commit is contained in:
parent
d358a6403e
commit
7047b8f32f
2 changed files with 36 additions and 55 deletions
|
@ -1,5 +1,5 @@
|
|||
use crossterm::event::KeyCode;
|
||||
use log::{error, info, warn};
|
||||
use log::error;
|
||||
use once_cell::sync::Lazy;
|
||||
use regex::Regex;
|
||||
use serde::de::DeserializeOwned;
|
||||
|
@ -14,8 +14,6 @@ use toml::Value;
|
|||
|
||||
use ratatui::style::{Color, Modifier};
|
||||
|
||||
const DEFAULT_CONFIG_PATH: &str = "/etc/lemurs/config.toml";
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct VarError {
|
||||
variable: String,
|
||||
|
@ -387,48 +385,19 @@ impl Default for Config {
|
|||
|
||||
impl Config {
|
||||
/// Facilitates the loading of the entire configuration
|
||||
pub fn load(path: Option<&Path>) -> Config {
|
||||
let mut should_crash = true;
|
||||
let load_config_path = path.unwrap_or_else(|| {
|
||||
should_crash = false;
|
||||
Path::new(DEFAULT_CONFIG_PATH)
|
||||
});
|
||||
|
||||
pub fn load(path: &Path) -> Result<Config, Box<dyn std::error::Error>> {
|
||||
let mut config = Config::default();
|
||||
|
||||
match load_as_parts(load_config_path) {
|
||||
Ok((config_str, var_config)) => {
|
||||
let config_str = apply_variables(config_str, &var_config);
|
||||
let partial = from_string::<PartialConfig, _>(&config_str);
|
||||
info!(
|
||||
"Successfully loaded configuration file from '{}'",
|
||||
load_config_path.display()
|
||||
);
|
||||
config.merge_in_partial(partial);
|
||||
}
|
||||
Err(err) => {
|
||||
if should_crash {
|
||||
eprintln!(
|
||||
"The config file '{}' cannot be loaded.\nReason: {}",
|
||||
load_config_path.display(),
|
||||
err
|
||||
);
|
||||
process::exit(1);
|
||||
} else {
|
||||
warn!(
|
||||
"No configuration file loaded from the expected location ({}). Reason: {}",
|
||||
DEFAULT_CONFIG_PATH, err
|
||||
);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
config
|
||||
let (config_str, var_config) = load_as_parts(path)?;
|
||||
let processed_config = apply_variables(config_str, &var_config)?;
|
||||
let partial = from_string::<PartialConfig, _>(&processed_config);
|
||||
config.merge_in_partial(partial);
|
||||
Ok(config)
|
||||
}
|
||||
}
|
||||
|
||||
/// Substitutes variables present in the configuration string
|
||||
fn apply_variables(config_str: String, var_config: &VariablesConfig) -> String {
|
||||
fn apply_variables(config_str: String, var_config: &VariablesConfig) -> Result<String, VarError> {
|
||||
static VARIABLE_REGEX: Lazy<Regex> = Lazy::new(|| {
|
||||
Regex::new(r"\$([a-zA-Z_][a-zA-Z0-9_]*)")
|
||||
.expect("Failed to compile the variable substitution regex")
|
||||
|
@ -442,18 +411,10 @@ fn apply_variables(config_str: String, var_config: &VariablesConfig) -> String {
|
|||
.map(|m| (m.start(), m.end(), m.as_str()))
|
||||
{
|
||||
let var_ident = &var[1..var.len()];
|
||||
let var_val = match var_config.variables.get(var_ident) {
|
||||
Some(val) => val,
|
||||
None => {
|
||||
let err = VarError {
|
||||
variable: var_ident.to_owned(),
|
||||
pos: start,
|
||||
};
|
||||
eprintln!("Given configuration file contains errors:");
|
||||
eprintln!("Failed to process variables: {}", err);
|
||||
std::process::exit(1);
|
||||
}
|
||||
};
|
||||
let var_val = var_config.variables.get(var_ident).ok_or(VarError {
|
||||
variable: var_ident.to_owned(),
|
||||
pos: start,
|
||||
})?;
|
||||
output.push_str(&config_str[last..start - 1]);
|
||||
|
||||
// any case that is not a string, will not be wrapped in brackets
|
||||
|
@ -470,7 +431,7 @@ fn apply_variables(config_str: String, var_config: &VariablesConfig) -> String {
|
|||
output.push_str(&config_str[last..config_len]);
|
||||
}
|
||||
|
||||
output
|
||||
Ok(output)
|
||||
}
|
||||
|
||||
/// Helper function to facilitate immediate deserialization of variables along passing the original file content
|
||||
|
|
26
src/main.rs
26
src/main.rs
|
@ -1,6 +1,6 @@
|
|||
use std::error::Error;
|
||||
use std::fs::File;
|
||||
use std::io;
|
||||
use std::{error::Error, path::Path};
|
||||
|
||||
use crossterm::{
|
||||
execute,
|
||||
|
@ -37,6 +37,7 @@ use self::{
|
|||
},
|
||||
};
|
||||
|
||||
const DEFAULT_CONFIG_PATH: &str = "/etc/lemurs/config.toml";
|
||||
const PREVIEW_LOG_PATH: &str = "lemurs.log";
|
||||
|
||||
fn setup_logger(log_path: &str) {
|
||||
|
@ -60,8 +61,27 @@ fn main() -> Result<(), Box<dyn Error>> {
|
|||
});
|
||||
|
||||
// Load and setup configuration
|
||||
let load_config_path = cli.config.as_deref();
|
||||
let mut config = Config::load(load_config_path);
|
||||
let mut should_crash = true;
|
||||
let cli_config_path = cli.config.as_deref();
|
||||
let load_config_path = cli_config_path.unwrap_or_else(|| {
|
||||
should_crash = false;
|
||||
Path::new(DEFAULT_CONFIG_PATH)
|
||||
});
|
||||
|
||||
let mut config = match Config::load(load_config_path) {
|
||||
Ok(config) => config,
|
||||
Err(err) => {
|
||||
eprintln!(
|
||||
"The config file '{}' cannot be loaded.\nReason: {}",
|
||||
load_config_path.display(),
|
||||
err
|
||||
);
|
||||
if should_crash {
|
||||
std::process::exit(1);
|
||||
}
|
||||
Config::default()
|
||||
}
|
||||
};
|
||||
|
||||
if let Some(cmd) = cli.command {
|
||||
match cmd {
|
||||
|
|
Loading…
Reference in a new issue