From 2b2c7bd5f718b0516d3a229e91ede5c0d2e32bb3 Mon Sep 17 00:00:00 2001 From: sigoden Date: Fri, 9 Jan 2026 16:43:18 +0800 Subject: [PATCH] feat: add option --allow-hash to allow/disallow file hashing (#657) --- README.md | 3 +++ src/args.rs | 12 ++++++++++++ src/server.rs | 6 +++++- tests/http.rs | 9 ++++++++- 4 files changed, 28 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 62ddbfe..d7bfcec 100644 --- a/README.md +++ b/README.md @@ -67,6 +67,7 @@ Options: --allow-search Allow search files/folders --allow-symlink Allow symlink to files/folders outside root directory --allow-archive Allow download folders as archive file + --allow-hash Allow ?hash query to get file sha256 hash --enable-cors Enable CORS, sets `Access-Control-Allow-Origin: *` --render-index Serve index.html when requesting a directory, returns 404 if not found index.html --render-try-index Serve index.html when requesting a directory, returns directory listing if not found index.html @@ -346,6 +347,7 @@ All options can be set using environment variables prefixed with `DUFS_`. --allow-search DUFS_ALLOW_SEARCH=true --allow-symlink DUFS_ALLOW_SYMLINK=true --allow-archive DUFS_ALLOW_ARCHIVE=true + --allow-hash DUFS_ALLOW_HASH=true --enable-cors DUFS_ENABLE_CORS=true --render-index DUFS_RENDER_INDEX=true --render-try-index DUFS_RENDER_TRY_INDEX=true @@ -383,6 +385,7 @@ allow-delete: true allow-search: true allow-symlink: true allow-archive: true +allow-hash: true enable-cors: true render-index: true render-try-index: true diff --git a/src/args.rs b/src/args.rs index 0ecce13..e756cf3 100644 --- a/src/args.rs +++ b/src/args.rs @@ -148,6 +148,14 @@ pub fn build_cli() -> Command { .action(ArgAction::SetTrue) .help("Allow download folders as archive file"), ) + .arg( + Arg::new("allow-hash") + .env("DUFS_ALLOW_HASH") + .hide_env(true) + .long("allow-hash") + .action(ArgAction::SetTrue) + .help("Allow ?hash query to get file sha256 hash"), + ) .arg( Arg::new("enable-cors") .env("DUFS_ENABLE_CORS") @@ -281,6 +289,7 @@ pub struct Args { pub allow_search: bool, pub allow_symlink: bool, pub allow_archive: bool, + pub allow_hash: bool, pub render_index: bool, pub render_spa: bool, pub render_try_index: bool, @@ -375,6 +384,9 @@ impl Args { if !args.allow_symlink { args.allow_symlink = allow_all || matches.get_flag("allow-symlink"); } + if !args.allow_hash { + args.allow_hash = allow_all || matches.get_flag("allow-hash"); + } if !args.allow_archive { args.allow_archive = allow_all || matches.get_flag("allow-archive"); } diff --git a/src/server.rs b/src/server.rs index 8028f93..a482829 100644 --- a/src/server.rs +++ b/src/server.rs @@ -358,7 +358,11 @@ impl Server { self.handle_edit_file(path, DataKind::View, head_only, user, &mut res) .await?; } else if has_query_flag(&query_params, "hash") { - self.handle_hash_file(path, head_only, &mut res).await?; + if self.args.allow_hash { + self.handle_hash_file(path, head_only, &mut res).await?; + } else { + status_forbid(&mut res); + } } else { self.handle_send_file(path, headers, head_only, &mut res) .await?; diff --git a/tests/http.rs b/tests/http.rs index 4627acc..df16a92 100644 --- a/tests/http.rs +++ b/tests/http.rs @@ -203,7 +203,7 @@ fn head_file(server: TestServer) -> Result<(), Error> { } #[rstest] -fn hash_file(server: TestServer) -> Result<(), Error> { +fn hash_file(#[with(&["--allow-hash"])] server: TestServer) -> Result<(), Error> { let resp = reqwest::blocking::get(format!("{}index.html?hash", server.url()))?; assert_eq!( resp.headers().get("content-type").unwrap(), @@ -217,6 +217,13 @@ fn hash_file(server: TestServer) -> Result<(), Error> { Ok(()) } +#[rstest] +fn no_hash_file(server: TestServer) -> Result<(), Error> { + let resp = reqwest::blocking::get(format!("{}index.html?hash", server.url()))?; + assert_eq!(resp.status(), 403); + Ok(()) +} + #[rstest] fn get_file_404(server: TestServer) -> Result<(), Error> { let resp = reqwest::blocking::get(format!("{}404", server.url()))?;