Improve app arguments management, can specify env file
This commit is contained in:
		
							
								
								
									
										7
									
								
								virtweb_backend/Cargo.lock
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										7
									
								
								virtweb_backend/Cargo.lock
									
									
									
										generated
									
									
									
								
							@@ -918,6 +918,12 @@ dependencies = [
 | 
			
		||||
 "subtle",
 | 
			
		||||
]
 | 
			
		||||
 | 
			
		||||
[[package]]
 | 
			
		||||
name = "dotenvy"
 | 
			
		||||
version = "0.15.7"
 | 
			
		||||
source = "registry+https://github.com/rust-lang/crates.io-index"
 | 
			
		||||
checksum = "1aaf95b3e5c8f23aa320147307562d361db0ae0d51242340f558153b4eb2439b"
 | 
			
		||||
 | 
			
		||||
[[package]]
 | 
			
		||||
name = "either"
 | 
			
		||||
version = "1.9.0"
 | 
			
		||||
@@ -2644,6 +2650,7 @@ dependencies = [
 | 
			
		||||
 "anyhow",
 | 
			
		||||
 "bytes",
 | 
			
		||||
 "clap",
 | 
			
		||||
 "dotenvy",
 | 
			
		||||
 "env_logger",
 | 
			
		||||
 "futures",
 | 
			
		||||
 "futures-util",
 | 
			
		||||
 
 | 
			
		||||
@@ -43,3 +43,4 @@ ipnetwork = "0.20.0"
 | 
			
		||||
num = "0.4.1"
 | 
			
		||||
rust-embed = { version = "8.1.0" }
 | 
			
		||||
mime_guess = "2.0.4"
 | 
			
		||||
dotenvy = "0.15.7"
 | 
			
		||||
@@ -8,6 +8,10 @@ use std::str::FromStr;
 | 
			
		||||
#[derive(Parser, Debug, Clone)]
 | 
			
		||||
#[clap(author, version, about, long_about = None)]
 | 
			
		||||
pub struct AppConfig {
 | 
			
		||||
    /// Read arguments from env file
 | 
			
		||||
    #[clap(short, long, env)]
 | 
			
		||||
    pub config: Option<String>,
 | 
			
		||||
 | 
			
		||||
    /// Listen address
 | 
			
		||||
    #[clap(short, long, env, default_value = "0.0.0.0:8000")]
 | 
			
		||||
    pub listen_address: String,
 | 
			
		||||
@@ -20,7 +24,7 @@ pub struct AppConfig {
 | 
			
		||||
    ///
 | 
			
		||||
    /// Warning! These origins won't be usable for OpenID authentication,
 | 
			
		||||
    /// only for local auth
 | 
			
		||||
    #[clap(long, env)]
 | 
			
		||||
    #[clap(short = 'o', long, env)]
 | 
			
		||||
    pub additional_origins: Vec<String>,
 | 
			
		||||
 | 
			
		||||
    /// Proxy IP, might end with a star "*"
 | 
			
		||||
@@ -28,7 +32,7 @@ pub struct AppConfig {
 | 
			
		||||
    pub proxy_ip: Option<String>,
 | 
			
		||||
 | 
			
		||||
    /// Secret key, used to sign some resources. Must be randomly generated
 | 
			
		||||
    #[clap(long, env, default_value = "")]
 | 
			
		||||
    #[clap(short = 'S', long, env, default_value = "")]
 | 
			
		||||
    secret: String,
 | 
			
		||||
 | 
			
		||||
    /// Specify whether the cookie should be transmitted only over secure connections
 | 
			
		||||
@@ -36,11 +40,11 @@ pub struct AppConfig {
 | 
			
		||||
    pub cookie_secure: bool,
 | 
			
		||||
 | 
			
		||||
    /// Auth username
 | 
			
		||||
    #[arg(long, env, default_value = "admin")]
 | 
			
		||||
    #[arg(short = 'u', long, env, default_value = "admin")]
 | 
			
		||||
    pub auth_username: String,
 | 
			
		||||
 | 
			
		||||
    /// Auth password
 | 
			
		||||
    #[arg(long, env, default_value = "admin")]
 | 
			
		||||
    #[arg(short = 'P', long, env, default_value = "admin")]
 | 
			
		||||
    pub auth_password: String,
 | 
			
		||||
 | 
			
		||||
    /// Disable authentication WARNING! THIS IS UNSECURE, it was designed only for development
 | 
			
		||||
@@ -88,16 +92,16 @@ pub struct AppConfig {
 | 
			
		||||
    ///
 | 
			
		||||
    /// Warning! This directory MUST be changed if `/tmp` is not in the same disk as the storage
 | 
			
		||||
    /// directory!
 | 
			
		||||
    #[arg(long, env, default_value = "/tmp")]
 | 
			
		||||
    #[arg(short, long, env, default_value = "/tmp")]
 | 
			
		||||
    pub temp_dir: String,
 | 
			
		||||
 | 
			
		||||
    /// Hypervisor URI. If not specified, "" will be used instead
 | 
			
		||||
    #[arg(long, env)]
 | 
			
		||||
    #[arg(short = 'H', long, env)]
 | 
			
		||||
    pub hypervisor_uri: Option<String>,
 | 
			
		||||
 | 
			
		||||
    /// Trusted network. If set, a client from a different will not be able to perform request other
 | 
			
		||||
    /// than those with GET verb (aside for login)
 | 
			
		||||
    #[arg(long, env)]
 | 
			
		||||
    #[arg(short = 'T', long, env)]
 | 
			
		||||
    pub trusted_network: Vec<String>,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@@ -108,6 +112,21 @@ lazy_static::lazy_static! {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
impl AppConfig {
 | 
			
		||||
    /// Parse environment variables from file, if requedst
 | 
			
		||||
    pub fn parse_env_file() -> anyhow::Result<()> {
 | 
			
		||||
        if let Some(c) = Self::parse().config {
 | 
			
		||||
            log::info!("Load additional environment variables from {c}");
 | 
			
		||||
            let conf_file = Path::new(&c);
 | 
			
		||||
 | 
			
		||||
            if !conf_file.is_file() {
 | 
			
		||||
                panic!("Specified configuration is not a file!");
 | 
			
		||||
            }
 | 
			
		||||
            dotenvy::from_path(conf_file)?;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        Ok(())
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /// Get parsed command line arguments
 | 
			
		||||
    pub fn get() -> &'static AppConfig {
 | 
			
		||||
        &ARGS
 | 
			
		||||
@@ -227,3 +246,14 @@ pub struct OIDCProvider<'a> {
 | 
			
		||||
    #[serde(skip_serializing)]
 | 
			
		||||
    pub configuration_url: &'a str,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#[cfg(test)]
 | 
			
		||||
mod test {
 | 
			
		||||
    use crate::app_config::AppConfig;
 | 
			
		||||
 | 
			
		||||
    #[test]
 | 
			
		||||
    fn verify_cli() {
 | 
			
		||||
        use clap::CommandFactory;
 | 
			
		||||
        AppConfig::command().debug_assert()
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -33,6 +33,9 @@ use virtweb_backend::utils::files_utils;
 | 
			
		||||
async fn main() -> std::io::Result<()> {
 | 
			
		||||
    env_logger::init_from_env(env_logger::Env::new().default_filter_or("info"));
 | 
			
		||||
 | 
			
		||||
    // Load additional config from file, if requested
 | 
			
		||||
    AppConfig::parse_env_file().unwrap();
 | 
			
		||||
 | 
			
		||||
    log::debug!("Create required directory, if missing");
 | 
			
		||||
    files_utils::create_directory_if_missing(AppConfig::get().iso_storage_path()).unwrap();
 | 
			
		||||
    files_utils::create_directory_if_missing(AppConfig::get().vnc_sockets_path()).unwrap();
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user