Add basic dbus proxy logic
This commit is contained in:
parent
f99ee75f98
commit
3f47840318
@ -1,4 +1,103 @@
|
|||||||
use log::{ debug, info, warn, error };
|
use log::{ debug, info, warn, error };
|
||||||
|
use dbus::{
|
||||||
|
nonblock::Proxy,
|
||||||
|
Error
|
||||||
|
};
|
||||||
|
use std::sync::Arc;
|
||||||
|
|
||||||
|
const DBUS_NAME: &'static str = "org.ddnss.sfs.mc";
|
||||||
|
|
||||||
|
fn iface_name(iface: &str) -> String {
|
||||||
|
DBUS_NAME.to_owned() + "." + iface
|
||||||
|
}
|
||||||
|
|
||||||
|
// #[non_exhaustive]
|
||||||
|
pub enum NativeObject<'proxy> {
|
||||||
|
Daemon(Proxy<'proxy, Arc<dbus::nonblock::SyncConnection>>),
|
||||||
|
Minecraft(Proxy<'proxy, Arc<dbus::nonblock::SyncConnection>>),
|
||||||
|
}
|
||||||
|
|
||||||
|
impl core::fmt::Debug for NativeObject<'_> {
|
||||||
|
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
|
||||||
|
write!(f, "NativeObject::").and(
|
||||||
|
match self {
|
||||||
|
Self::Daemon(_) => f.debug_tuple("Daemon"),
|
||||||
|
Self::Minecraft(_) => f.debug_tuple("Minecraft")
|
||||||
|
}.field(&"_").finish()
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'proxy> NativeObject<'proxy> {
|
||||||
|
pub fn new(c: Arc<dbus::nonblock::SyncConnection>, path: &'proxy str) -> Self {
|
||||||
|
match path {
|
||||||
|
"/" => Self::Daemon(Proxy::<'proxy>::new(DBUS_NAME, path, std::time::Duration::from_secs(5), c)),
|
||||||
|
"/minecraft" => Self::Minecraft(Proxy::<'proxy>::new(DBUS_NAME, path, std::time::Duration::from_secs(5), c)),
|
||||||
|
_ => panic!("Unknown object path {:?}", path)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn no_path<MD: core::fmt::Display, VD: core::fmt::Debug>(method: MD, variant: VD) -> ! {
|
||||||
|
panic!("No method {} on variant {:?}", method, variant)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub async fn start(&self) -> Result<(), Error> {
|
||||||
|
let proxy = match self {
|
||||||
|
Self::Daemon(p) | Self::Minecraft(p) => p,
|
||||||
|
_ => Self::no_path("start", self)
|
||||||
|
};
|
||||||
|
|
||||||
|
proxy.method_call(iface_name("Service"), "Start", ()).await
|
||||||
|
}
|
||||||
|
|
||||||
|
pub async fn stop(&self) -> Result<(), Error> {
|
||||||
|
let proxy = match self {
|
||||||
|
Self::Daemon(p) | Self::Minecraft(p) => p,
|
||||||
|
_ => Self::no_path("stop", self)
|
||||||
|
};
|
||||||
|
|
||||||
|
let res = proxy.method_call(iface_name("Service"), "Stop", ()).await;
|
||||||
|
res.or_else(|err|
|
||||||
|
if
|
||||||
|
proxy.path.to_string() == "/".to_owned() &&
|
||||||
|
err.name() == Some("org.freedesktop.DBus.Error.NoReply") &&
|
||||||
|
err.message() == Some("Message recipient disconnected from message bus without replying")
|
||||||
|
{
|
||||||
|
Ok(())
|
||||||
|
} else {
|
||||||
|
Err(err)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub async fn is_running(&self) -> bool {
|
||||||
|
let proxy = match self {
|
||||||
|
Self::Daemon(p) | Self::Minecraft(p) => p,
|
||||||
|
_ => Self::no_path("is_running", self)
|
||||||
|
};
|
||||||
|
|
||||||
|
let res = proxy.method_call(iface_name("Service"), "IsRunning", ()).await;
|
||||||
|
res.map(|data: (bool,)| data.0).or_else(|err|
|
||||||
|
if
|
||||||
|
proxy.path.to_string() == "/".to_string() &&
|
||||||
|
err.name() == Some("org.freedesktop.DBus.Error.ServiceUnknown")
|
||||||
|
{
|
||||||
|
Ok(false)
|
||||||
|
} else {
|
||||||
|
Err(err)
|
||||||
|
}
|
||||||
|
).unwrap()
|
||||||
|
}
|
||||||
|
|
||||||
|
pub async fn restart(&self) -> Result<(), Error> {
|
||||||
|
let proxy = match self {
|
||||||
|
Self::Daemon(p) | Self::Minecraft(p) => p,
|
||||||
|
_ => Self::no_path("restart", self)
|
||||||
|
};
|
||||||
|
|
||||||
|
proxy.method_call(iface_name("Service"), "Restart", ()).await
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[tokio::main]
|
#[tokio::main]
|
||||||
async fn main() -> Result<(), Box<dyn std::error::Error>> {
|
async fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||||
@ -21,8 +120,12 @@ async fn main() -> Result<(), Box<dyn std::error::Error>> {
|
|||||||
panic!("Lost connection to D-Bus: {}", err);
|
panic!("Lost connection to D-Bus: {}", err);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Get a proxy connection to the daemon
|
||||||
|
let daemon = NativeObject::new(c, "/");
|
||||||
|
|
||||||
// TODO:
|
// TODO:
|
||||||
// Perform operations
|
// Perform operations
|
||||||
|
info!("The daemon is{} running", if !daemon.is_running().await {"n't"} else {""});
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
Loading…
Reference in New Issue
Block a user