|
|
|
|
|
|
|
use crate::handler::paths::{file_path, FileType}; |
|
|
|
use super::parser_models::Style; |
|
use log::LevelFilter; |
|
use rlua::Lua; |
|
use std::{collections::HashMap, fs, thread::available_parallelism}; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#[derive(Clone)] |
|
pub struct Config { |
|
pub port: u16, |
|
pub binding_ip: String, |
|
pub style: Style, |
|
pub redis_url: String, |
|
pub aggregator: AggregatorConfig, |
|
pub logging: bool, |
|
pub debug: bool, |
|
pub upstream_search_engines: Vec<crate::engines::engine_models::EngineHandler>, |
|
pub request_timeout: u8, |
|
pub threads: u8, |
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#[derive(Clone)] |
|
pub struct AggregatorConfig { |
|
pub random_delay: bool, |
|
} |
|
|
|
impl Config { |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
pub fn parse(logging_initialized: bool) -> Result<Self, Box<dyn std::error::Error>> { |
|
Lua::new().context(|context| -> Result<Self, Box<dyn std::error::Error>> { |
|
let globals = context.globals(); |
|
|
|
context |
|
.load(&fs::read_to_string(file_path(FileType::Config)?)?) |
|
.exec()?; |
|
|
|
let parsed_threads: u8 = globals.get::<_, u8>("threads")?; |
|
|
|
let debug: bool = globals.get::<_, bool>("debug")?; |
|
let logging:bool= globals.get::<_, bool>("logging")?; |
|
|
|
if !logging_initialized { |
|
set_logging_level(debug, logging); |
|
} |
|
|
|
let threads: u8 = if parsed_threads == 0 { |
|
let total_num_of_threads: usize = available_parallelism()?.get() / 2; |
|
log::error!("Config Error: The value of `threads` option should be a non zero positive integer"); |
|
log::error!("Falling back to using {} threads", total_num_of_threads); |
|
total_num_of_threads as u8 |
|
} else { |
|
parsed_threads |
|
}; |
|
|
|
Ok(Config { |
|
port: globals.get::<_, u16>("port")?, |
|
binding_ip: globals.get::<_, String>("binding_ip")?, |
|
style: Style::new( |
|
globals.get::<_, String>("theme")?, |
|
globals.get::<_, String>("colorscheme")?, |
|
), |
|
redis_url: globals.get::<_, String>("redis_url")?, |
|
aggregator: AggregatorConfig { |
|
random_delay: globals.get::<_, bool>("production_use")?, |
|
}, |
|
logging, |
|
debug, |
|
upstream_search_engines: globals |
|
.get::<_, HashMap<String, bool>>("upstream_search_engines")? |
|
.into_iter() |
|
.filter_map(|(key, value)| value.then_some(key)) |
|
.filter_map(|engine| crate::engines::engine_models::EngineHandler::new(&engine)) |
|
.collect(), |
|
request_timeout: globals.get::<_, u8>("request_timeout")?, |
|
threads, |
|
}) |
|
}) |
|
} |
|
} |
|
|
|
|
|
fn set_logging_level(debug: bool, logging: bool) { |
|
if let Ok(pkg_env_var) = std::env::var("PKG_ENV") { |
|
if pkg_env_var.to_lowercase() == "dev" { |
|
env_logger::Builder::new() |
|
.filter(None, LevelFilter::Trace) |
|
.init(); |
|
return; |
|
} |
|
} |
|
|
|
|
|
let log_level = match (debug, logging) { |
|
(true, true) => LevelFilter::Debug, |
|
(true, false) => LevelFilter::Debug, |
|
(false, true) => LevelFilter::Info, |
|
(false, false) => LevelFilter::Error, |
|
}; |
|
|
|
env_logger::Builder::new().filter(None, log_level).init(); |
|
} |
|
|