diff --git a/crates/ptth_server/src/file_server.rs b/crates/ptth_server/src/file_server.rs index cacf115..68aaf62 100644 --- a/crates/ptth_server/src/file_server.rs +++ b/crates/ptth_server/src/file_server.rs @@ -5,7 +5,7 @@ use std::{ cmp::min, - collections::HashMap, + collections::*, convert::{Infallible, TryFrom}, io::SeekFrom, path::{ @@ -56,6 +56,7 @@ use errors::FileServerError; #[derive (Default)] pub struct Config { pub file_server_root: PathBuf, + pub file_server_roots: BTreeMap , } pub struct FileServer { @@ -68,7 +69,7 @@ pub struct FileServer { impl FileServer { pub fn new ( - file_server_root: PathBuf, + config: Config, asset_root: &Path, name: String, metrics_interval: Arc >>, @@ -76,9 +77,7 @@ impl FileServer { ) -> Result { Ok (Self { - config: Config { - file_server_root, - }, + config, handlebars: load_templates (asset_root)?, metrics_startup: metrics::Startup::new (name), metrics_interval, @@ -374,9 +373,12 @@ impl FileServer { resp } - let root: &std::path::Path = &self.config.file_server_root; + let roots = internal::FileRoots { + files: &self.config.file_server_root, + dirs: &self.config.file_server_roots, + }; - Ok (match internal::serve_all (root, method, uri, headers, self.hidden_path.as_deref ()).await? { + Ok (match internal::serve_all (roots, method, uri, headers, self.hidden_path.as_deref ()).await? { Favicon => serve_error (StatusCode::NotFound, "Not found\n"), Forbidden => serve_error (StatusCode::Forbidden, "403 Forbidden\n"), MethodNotAllowed => serve_error (StatusCode::MethodNotAllowed, "Unsupported method\n"), diff --git a/crates/ptth_server/src/file_server/internal.rs b/crates/ptth_server/src/file_server/internal.rs index 1c29fd3..c052a35 100644 --- a/crates/ptth_server/src/file_server/internal.rs +++ b/crates/ptth_server/src/file_server/internal.rs @@ -4,7 +4,7 @@ // human-readable HTML use std::{ - collections::HashMap, + collections::*, path::{Path, PathBuf}, }; @@ -244,11 +244,17 @@ async fn serve_api ( Ok (NotFound) } +#[derive (Clone, Copy)] +pub struct FileRoots <'a> { + pub files: &'a Path, + pub dirs: &'a BTreeMap , +} + // Handle the requests internally without knowing anything about PTTH or // HTML / handlebars pub async fn serve_all ( - root: &Path, + roots: FileRoots <'_>, method: Method, uri: &str, headers: &HashMap >, @@ -283,7 +289,7 @@ pub async fn serve_all ( } if let Some (path) = path.strip_prefix ("/api") { - return serve_api (root, &uri, hidden_path, path).await; + return serve_api (roots.files, &uri, hidden_path, path).await; } let path = match path.strip_prefix ("/files/") { @@ -298,7 +304,7 @@ pub async fn serve_all ( let path_s = percent_decode (encoded_path.as_bytes ()).decode_utf8 ().map_err (FileServerError::PathNotUtf8)?; let path = Path::new (&*path_s); - let full_path = root.join (path); + let full_path = roots.files.join (path); trace! ("full_path = {:?}", full_path); diff --git a/crates/ptth_server/src/lib.rs b/crates/ptth_server/src/lib.rs index c90093d..2a50548 100644 --- a/crates/ptth_server/src/lib.rs +++ b/crates/ptth_server/src/lib.rs @@ -319,7 +319,10 @@ pub async fn run_server ( }); let file_server = file_server::FileServer::new ( - config_file.file_server_root.clone (), + file_server::Config { + file_server_root: config_file.file_server_root.clone (), + file_server_roots: config_file.file_server_roots.clone (), + }, &asset_root.clone ().unwrap_or_else (|| PathBuf::from (".")), config_file.name.clone (), metrics_interval,