aboutsummaryrefslogtreecommitdiffstats
path: root/src/listing.rs
diff options
context:
space:
mode:
authorLukas Stabe <lukas@stabe.de>2020-09-24 03:22:45 +0000
committerLukas Stabe <lukas@stabe.de>2020-09-24 03:22:45 +0000
commit746535b7645b6aeb6eb58dced984530744fef161 (patch)
tree58b5a8df0d9185fc707e7c57104af21b58db1aa5 /src/listing.rs
parentSorry cargo fmt (diff)
downloadminiserve-746535b7645b6aeb6eb58dced984530744fef161.tar.gz
miniserve-746535b7645b6aeb6eb58dced984530744fef161.zip
add title option (#335) and breadcrumb links in heading
Diffstat (limited to 'src/listing.rs')
-rw-r--r--src/listing.rs50
1 files changed, 42 insertions, 8 deletions
diff --git a/src/listing.rs b/src/listing.rs
index a70e237..7f09fa4 100644
--- a/src/listing.rs
+++ b/src/listing.rs
@@ -8,7 +8,7 @@ use percent_encoding::{percent_decode_str, utf8_percent_encode, AsciiSet, CONTRO
use qrcodegen::{QrCode, QrCodeEcc};
use serde::Deserialize;
use std::io;
-use std::path::{Path, PathBuf};
+use std::path::{Component, Path, PathBuf};
use std::time::SystemTime;
use strum_macros::{Display, EnumString};
@@ -123,6 +123,21 @@ impl Entry {
}
}
+/// One entry in the path to the listed directory
+pub struct Breadcrumb {
+ /// Name of directory
+ pub name: String,
+
+ /// Link to get to directory, relative to listed directory
+ pub link: String,
+}
+
+impl Breadcrumb {
+ fn new(name: String, link: String) -> Self {
+ Breadcrumb { name, link }
+ }
+}
+
pub async fn file_handler(req: HttpRequest) -> Result<actix_files::NamedFile> {
let path = &req.app_data::<crate::MiniserveConfig>().unwrap().path;
actix_files::NamedFile::open(path).map_err(Into::into)
@@ -143,6 +158,7 @@ pub fn directory_listing(
upload_route: String,
tar_enabled: bool,
zip_enabled: bool,
+ title: Option<String>,
) -> Result<ServiceResponse, io::Error> {
use actix_web::dev::BodyEncoding;
let serve_path = req.path();
@@ -173,13 +189,31 @@ pub fn directory_listing(
.display()
.to_string();
- let display_dir = {
+ let connection_info = actix_web::dev::ConnectionInfo::get(req.head(), req.app_config());
+ let title = title.unwrap_or_else(|| connection_info.host().into());
+
+ let breadcrumbs = {
let decoded = percent_decode_str(&encoded_dir).decode_utf8_lossy();
- if is_root {
- decoded.to_string()
- } else {
- format!("{}/", decoded)
- }
+ let components = Path::new(&*decoded).components();
+ components
+ .collect::<Vec<_>>()
+ .iter()
+ .rev()
+ .enumerate()
+ .rev()
+ .map(|(i, c)| {
+ let link = if i == 0 {
+ ".".into()
+ } else {
+ (0..i).map(|_| "..").collect::<Vec<_>>().join("/")
+ };
+ match c {
+ Component::RootDir => Breadcrumb::new(title.clone(), link),
+ Component::Normal(s) => Breadcrumb::new(s.to_string_lossy().into(), link),
+ _ => panic!(""),
+ }
+ })
+ .collect()
};
let query_params = extract_query_parameters(req);
@@ -360,7 +394,7 @@ pub fn directory_listing(
&upload_route,
&favicon_route,
&encoded_dir,
- &display_dir,
+ breadcrumbs,
tar_enabled,
zip_enabled,
)