Repository: sigoden/dufs (Rust)

Issue:
simplest launch command to be readonly for everyone
## Specific Demand

i want simplest launch command to serve file be readonly for everyone
currently i use `dufs -A -a @/`
but it still renders edit and delete buttons, which prompt auth dialog when clicked. this ui is unwanted.

## Implement Suggestion

provide a command to serve readonly files for everyone, and ui having no edit and delete buttons.
 
 


Discussion:

Patch:
diff --git a/src/server.rs b/src/server.rs
index f83ea4af4..fea590dc3 100644
--- a/src/server.rs
+++ b/src/server.rs
@@ -460,7 +460,7 @@ impl Server {
     ) -> Result<()> {
         let mut paths = vec![];
         if exist {
-            paths = match self.list_dir(path, path, access_paths).await {
+            paths = match self.list_dir(path, path, access_paths.clone()).await {
                 Ok(paths) => paths,
                 Err(_) => {
                     status_forbid(res);
@@ -468,7 +468,16 @@ impl Server {
                 }
             }
         };
-        self.send_index(path, paths, exist, query_params, head_only, user, res)
+        self.send_index(
+            path,
+            paths,
+            exist,
+            query_params,
+            head_only,
+            user,
+            access_paths,
+            res,
+        )
     }
 
     async fn handle_search_dir(
@@ -490,6 +499,7 @@ impl Server {
             let hidden = Arc::new(self.args.hidden.to_vec());
             let hidden = hidden.clone();
             let running = self.running.clone();
+            let access_paths = access_paths.clone();
             let search_paths = tokio::task::spawn_blocking(move || {
                 let mut paths: Vec<PathBuf> = vec![];
                 for dir in access_paths.leaf_paths(&path_buf) {
@@ -534,7 +544,16 @@ impl Server {
                 }
             }
         }
-        self.send_index(path, paths, true, query_params, head_only, user, res)
+        self.send_index(
+            path,
+            paths,
+            true,
+            query_params,
+            head_only,
+            user,
+            access_paths,
+            res,
+        )
     }
 
     async fn handle_zip_dir(
@@ -928,6 +947,7 @@ impl Server {
         query_params: &HashMap<String, String>,
         head_only: bool,
         user: Option<String>,
+        access_paths: AccessPaths,
         res: &mut Response,
     ) -> Result<()> {
         if let Some(sort) = query_params.get("sort") {
@@ -988,12 +1008,13 @@ impl Server {
             return Ok(());
         }
         let href = format!("/{}", normalize_path(path.strip_prefix(&self.args.path)?));
+        let readwrite = access_paths.perm().readwrite();
         let data = IndexData {
             kind: DataKind::Index,
             href,
             uri_prefix: self.args.uri_prefix.clone(),
-            allow_upload: self.args.allow_upload,
-            allow_delete: self.args.allow_delete,
+            allow_upload: self.args.allow_upload && readwrite,
+            allow_delete: self.args.allow_delete && readwrite,
             allow_search: self.args.allow_search,
             allow_archive: self.args.allow_archive,
             dir_exists: exist,


Test patch:
diff --git a/tests/auth.rs b/tests/auth.rs
index 0111cfd66..41b943648 100644
--- a/tests/auth.rs
+++ b/tests/auth.rs
@@ -213,3 +213,22 @@ fn no_auth_propfind_dir(
     assert!(body.contains("<D:href>/dir1/</D:href>"));
     Ok(())
 }
+
+#[rstest]
+fn auth_data(
+    #[with(&["--auth", "user:pass@/:rw|@/", "-A", "--auth-method", "basic"])] server: TestServer,
+) -> Result<(), Error> {
+    let resp = reqwest::blocking::get(server.url())?;
+    let content = resp.text()?;
+    let json = utils::retrive_json(&content).unwrap();
+    assert_eq!(json["allow_delete"], serde_json::Value::Bool(false));
+    assert_eq!(json["allow_upload"], serde_json::Value::Bool(false));
+    let resp = fetch!(b"GET", server.url())
+        .basic_auth("user", Some("pass"))
+        .send()?;
+    let content = resp.text()?;
+    let json = utils::retrive_json(&content).unwrap();
+    assert_eq!(json["allow_delete"], serde_json::Value::Bool(true));
+    assert_eq!(json["allow_upload"], serde_json::Value::Bool(true));
+    Ok(())
+}
diff --git a/tests/utils.rs b/tests/utils.rs
index c40be5e1b..90d3f5418 100644
--- a/tests/utils.rs
+++ b/tests/utils.rs
@@ -59,7 +59,8 @@ pub fn encode_uri(v: &str) -> String {
     parts.join("/")
 }
 
-fn retrive_json(content: &str) -> Option<Value> {
+#[allow(dead_code)]
+pub fn retrive_json(content: &str) -> Option<Value> {
     let lines: Vec<&str> = content.lines().collect();
     let line = lines.iter().find(|v| v.contains("DATA ="))?;
     let line_col = line.find("DATA =").unwrap() + 6;