Add base server
This commit is contained in:
		
							
								
								
									
										124
									
								
								virtweb_backend/src/app_config.rs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										124
									
								
								virtweb_backend/src/app_config.rs
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,124 @@
 | 
			
		||||
use clap::Parser;
 | 
			
		||||
 | 
			
		||||
/// VirtWeb backend API
 | 
			
		||||
#[derive(Parser, Debug, Clone)]
 | 
			
		||||
#[clap(author, version, about, long_about = None)]
 | 
			
		||||
pub struct AppConfig {
 | 
			
		||||
    /// Listen address
 | 
			
		||||
    #[clap(short, long, env, default_value = "0.0.0.0:8000")]
 | 
			
		||||
    pub listen_address: String,
 | 
			
		||||
 | 
			
		||||
    /// Website origin
 | 
			
		||||
    #[clap(short, long, env, default_value = "http://localhost:3000")]
 | 
			
		||||
    pub website_origin: String,
 | 
			
		||||
 | 
			
		||||
    /// Proxy IP, might end with a star "*"
 | 
			
		||||
    #[clap(short, long, env)]
 | 
			
		||||
    pub proxy_ip: Option<String>,
 | 
			
		||||
 | 
			
		||||
    /// Secret key, used to sign some resources. Must be randomly generated
 | 
			
		||||
    #[clap(long, env, default_value = "")]
 | 
			
		||||
    secret: String,
 | 
			
		||||
 | 
			
		||||
    /// Auth username
 | 
			
		||||
    #[arg(long, env, default_value = "admin")]
 | 
			
		||||
    pub auth_username: String,
 | 
			
		||||
 | 
			
		||||
    /// Auth password
 | 
			
		||||
    #[arg(long, env, default_value = "admin")]
 | 
			
		||||
    pub auth_password: String,
 | 
			
		||||
 | 
			
		||||
    /// Disable local auth
 | 
			
		||||
    #[arg(long, env)]
 | 
			
		||||
    pub disable_local_auth: bool,
 | 
			
		||||
 | 
			
		||||
    /// Request header that can be added by a reverse proxy to disable local authentication
 | 
			
		||||
    #[arg(long, env, default_value = "X-Disable-Local-Auth")]
 | 
			
		||||
    pub disable_auth_header_token: String,
 | 
			
		||||
 | 
			
		||||
    /// URL where the OpenID configuration can be found
 | 
			
		||||
    #[arg(
 | 
			
		||||
    long,
 | 
			
		||||
    env,
 | 
			
		||||
    default_value = "http://localhost:9001/.well-known/openid-configuration"
 | 
			
		||||
    )]
 | 
			
		||||
    pub oidc_configuration_url: String,
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    /// Disable OpenID authentication
 | 
			
		||||
    #[arg(long, env)]
 | 
			
		||||
    pub disable_oidc: bool,
 | 
			
		||||
 | 
			
		||||
    /// OpenID client ID
 | 
			
		||||
    #[arg(long, env, default_value = "foo")]
 | 
			
		||||
    pub oidc_client_id: String,
 | 
			
		||||
 | 
			
		||||
    /// OpenID client secret
 | 
			
		||||
    #[arg(long, env, default_value = "bar")]
 | 
			
		||||
    pub oidc_client_secret: String,
 | 
			
		||||
 | 
			
		||||
    /// OpenID login redirect URL
 | 
			
		||||
    #[arg(long, env, default_value = "APP_ORIGIN/oidc_cb")]
 | 
			
		||||
    oidc_redirect_url: String,
 | 
			
		||||
 | 
			
		||||
    /// Directory where temporary files are stored
 | 
			
		||||
    #[arg(long, env, default_value = "/tmp")]
 | 
			
		||||
    pub temp_dir: String,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
lazy_static::lazy_static! {
 | 
			
		||||
    static ref ARGS: AppConfig = {
 | 
			
		||||
        AppConfig::parse()
 | 
			
		||||
    };
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
impl AppConfig {
 | 
			
		||||
    /// Get parsed command line arguments
 | 
			
		||||
    pub fn get() -> &'static AppConfig {
 | 
			
		||||
        &ARGS
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /// Get app secret
 | 
			
		||||
    pub fn secret(&self) -> &str {
 | 
			
		||||
        let mut secret = self.secret.as_str();
 | 
			
		||||
 | 
			
		||||
        if cfg!(debug_assertions) && secret.is_empty() {
 | 
			
		||||
            secret = "DEBUGKEYDEBUGKEYDEBUGKEYDEBUGKEYDEBUGKEY";
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if secret.is_empty() {
 | 
			
		||||
            panic!("SECRET is undefined or too short (min 30 chars)!")
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        secret
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /// Get OpenID providers configuration
 | 
			
		||||
    pub fn openid_provider(&self) -> Option<OIDCProvider<'_>> {
 | 
			
		||||
        if self.disable_oidc {
 | 
			
		||||
            return None;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        Some(OIDCProvider {
 | 
			
		||||
            client_id: self.oidc_client_id.as_str(),
 | 
			
		||||
            client_secret: self.oidc_client_secret.as_str(),
 | 
			
		||||
            configuration_url: self.oidc_configuration_url.as_str(),
 | 
			
		||||
        })
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /// Get OIDC callback URL
 | 
			
		||||
    pub fn oidc_redirect_url(&self) -> String {
 | 
			
		||||
        self.oidc_redirect_url
 | 
			
		||||
            .replace("APP_ORIGIN", &self.website_origin)
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#[derive(Debug, Clone, serde::Serialize)]
 | 
			
		||||
pub struct OIDCProvider<'a> {
 | 
			
		||||
    #[serde(skip_serializing)]
 | 
			
		||||
    pub client_id: &'a str,
 | 
			
		||||
    #[serde(skip_serializing)]
 | 
			
		||||
    pub client_secret: &'a str,
 | 
			
		||||
    #[serde(skip_serializing)]
 | 
			
		||||
    pub configuration_url: &'a str,
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										1
									
								
								virtweb_backend/src/controllers/mod.rs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										1
									
								
								virtweb_backend/src/controllers/mod.rs
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1 @@
 | 
			
		||||
pub mod server_controller;
 | 
			
		||||
							
								
								
									
										5
									
								
								virtweb_backend/src/controllers/server_controller.rs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										5
									
								
								virtweb_backend/src/controllers/server_controller.rs
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,5 @@
 | 
			
		||||
use actix_web::{HttpResponse, Responder};
 | 
			
		||||
 | 
			
		||||
pub async fn root_index() -> impl Responder {
 | 
			
		||||
    HttpResponse::Ok().body("Hello world!")
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										2
									
								
								virtweb_backend/src/lib.rs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										2
									
								
								virtweb_backend/src/lib.rs
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,2 @@
 | 
			
		||||
pub mod app_config;
 | 
			
		||||
pub mod controllers;
 | 
			
		||||
@@ -1,3 +1,24 @@
 | 
			
		||||
fn main() {
 | 
			
		||||
    println!("Hello, world!");
 | 
			
		||||
use actix_remote_ip::RemoteIPConfig;
 | 
			
		||||
use actix_web::{App, HttpServer, web};
 | 
			
		||||
use virtweb_backend::app_config::AppConfig;
 | 
			
		||||
use actix_web::middleware::Logger;
 | 
			
		||||
use virtweb_backend::controllers::server_controller;
 | 
			
		||||
 | 
			
		||||
#[actix_web::main]
 | 
			
		||||
async fn main() -> std::io::Result<()> {
 | 
			
		||||
    env_logger::init_from_env(env_logger::Env::new().default_filter_or("info"));
 | 
			
		||||
 | 
			
		||||
    log::info!("Start to listen on {}", AppConfig::get().listen_address);
 | 
			
		||||
 | 
			
		||||
    HttpServer::new(|| {
 | 
			
		||||
        App::new()
 | 
			
		||||
            .wrap(Logger::default())
 | 
			
		||||
            .app_data(web::Data::new(RemoteIPConfig {
 | 
			
		||||
                proxy: AppConfig::get().proxy_ip.clone()
 | 
			
		||||
            }))
 | 
			
		||||
            .route("/", web::get().to(server_controller::root_index))
 | 
			
		||||
    })
 | 
			
		||||
        .bind(&AppConfig::get().listen_address)?
 | 
			
		||||
        .run()
 | 
			
		||||
        .await
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user