Initial commit

This commit is contained in:
Natty 2024-02-03 17:03:43 +01:00
commit 390a84dd06
Signed by: natty
GPG Key ID: BF6CB659ADEE60EC
5 changed files with 1789 additions and 0 deletions

1
.gitignore vendored Normal file
View File

@ -0,0 +1 @@
/target

1634
Cargo.lock generated Normal file

File diff suppressed because it is too large Load Diff

18
Cargo.toml Normal file
View File

@ -0,0 +1,18 @@
[package]
name = "dfmd"
version = "0.1.0"
license = "MIT OR GPL-3.0-only"
edition = "2021"
[dependencies]
thiserror = { version = "1" }
eyre = { version = "0.6" }
tokio = { version = "1", features = ["rt", "process", "macros"] }
zbus = { version = "3.14", features = ["tokio"] }
zbus_macros = { version = "3.14" }
clap = { version = "4.4", features = ["derive"] }
tracing = { version = "0.1" }
tracing-subscriber = { version = "0.3" }
[profile.release]
lto = true

43
README.md Normal file
View File

@ -0,0 +1,43 @@
# dfmd
A small utility daemon to handle "open containing folder" activities in various
software.
🦊
## Dependencies
- DBus
- xdg-open as the default handler
## Building
```
cargo build --release
```
## Configuration
Use the DFMD_*_PROGRAM environment variables. `%ARGS%` is substituted with a
list of input files.
### Default handler programs
```
DFMD_FOLDER_PROGRAM: echo %ARGS% | xargs -n1 xdg-open
DFMD_ITEMS_PROGRAM: echo %ARGS% | xargs -d " " -I {} sh -c 'p="{}"; echo "${p%/*}"' | xargs -n1 xdg-open
DFMD_PROPERTIES_PROGRAM: echo %ARGS% | xargs -n1 xdg-open
```
## Autostart
Create a DBus service in
`$XDG_DATA_HOME/dbus-1/services/org.freedesktop.FileManager1.service`.
(The default directory for `XDG_DATA_HOME` is `$HOME/.local/share/`)
```
[D-BUS Service]
Name=org.freedesktop.FileManager1
Exec=path/to/dfmd
```

93
src/main.rs Normal file
View File

@ -0,0 +1,93 @@
use std::{env, future::pending};
use tokio::process;
use tracing::{error, info, Level};
use zbus::ConnectionBuilder;
use zbus_macros::dbus_interface;
struct FileManager {
show_folder_program: String,
show_items_program: String,
show_properties_program: String,
}
#[dbus_interface(name = "org.freedesktop.FileManager1")]
impl FileManager {
async fn show_folders(&self, ref uris: Vec<String>, _startup_id: &str) {
process::Command::new("sh")
.args([
"-c",
&self.show_folder_program.replace("%ARGS%", &uris.join(" ")),
])
.spawn()
.map_err(|e| {
error!("Failed to run file manager: {}", e);
e
})
.ok();
}
async fn show_items(&self, uris: Vec<String>, _startup_id: &str) {
let cmd = self.show_items_program.replace("%ARGS%", &uris.join(" "));
info!("Executing: {}", cmd);
process::Command::new("sh")
.args(["-c", &cmd])
.spawn()
.map_err(|e| {
error!("Failed to run file manager: {}", e);
e
})
.ok();
}
async fn show_item_properties(&self, ref uris: Vec<String>, _startup_id: &str) {
process::Command::new("sh")
.args([
"-c",
&self
.show_properties_program
.replace("%ARGS%", &uris.join(" ")),
])
.spawn()
.map_err(|e| {
error!("Failed to run file manager: {}", e);
e
})
.ok();
}
}
#[tokio::main(flavor = "current_thread")]
async fn main() -> eyre::Result<()> {
tracing_subscriber::fmt().with_max_level(Level::INFO).init();
let show_folder_program = env::var("DFMD_FOLDER_PROGRAM")
.ok()
.unwrap_or_else(|| r#"echo %ARGS% | xargs -n1 xdg-open"#.to_string());
let show_items_program = env::var("DFMD_ITEMS_PROGRAM").ok().unwrap_or_else(||
r#"echo %ARGS% | xargs -d " " -I {} sh -c 'p="{}"; echo "${p%/*}"' | xargs -n1 xdg-open"#.to_string(),
);
let show_properties_program = env::var("DFMD_PROPERTIES_PROGRAM")
.ok()
.unwrap_or_else(|| r#"echo %ARGS% | xargs -n1 xdg-open"#.to_string());
let _conn = ConnectionBuilder::session()?
.name("org.freedesktop.FileManager1")?
.serve_at(
"/org/freedesktop/FileManager1",
FileManager {
show_folder_program,
show_items_program,
show_properties_program,
},
)?
.build()
.await?;
pending::<()>().await;
Ok(())
}