use std::{collections::HashMap, os::fd::BorrowedFd, path::Path};
use enumflags2::{bitflags, BitFlags};
use futures_util::Stream;
use serde_repr::{Deserialize_repr, Serialize_repr};
use zbus::zvariant::{Fd, Type};
use crate::{proxy::Proxy, Error, FilePath};
#[bitflags]
#[derive(Serialize_repr, Deserialize_repr, PartialEq, Eq, Copy, Clone, Debug, Type)]
#[repr(u32)]
pub enum HostCommandFlags {
#[doc(alias = "FLATPAK_HOST_COMMAND_FLAGS_CLEAR_ENV")]
ClearEnv,
#[doc(alias = "FLATPAK_HOST_COMMAND_FLAGS_WATCH_BUS")]
WatchBus,
}
#[derive(Debug)]
#[doc(alias = "org.freedesktop.Flatpak.Development")]
pub struct Development<'a>(Proxy<'a>);
impl<'a> Development<'a> {
pub async fn new() -> Result<Development<'a>, Error> {
let proxy = Proxy::new_flatpak_development("org.freedesktop.Flatpak.Development").await?;
Ok(Self(proxy))
}
#[doc(alias = "HostCommandExited")]
pub async fn receive_spawn_exited(&self) -> Result<impl Stream<Item = (u32, u32)>, Error> {
self.0.signal("HostCommandExited").await
}
pub async fn host_command(
&self,
cwd_path: impl AsRef<Path>,
argv: &[impl AsRef<Path>],
fds: HashMap<u32, BorrowedFd<'_>>,
envs: HashMap<&str, &str>,
flags: BitFlags<HostCommandFlags>,
) -> Result<u32, Error> {
let cwd_path = FilePath::new(cwd_path)?;
let argv = argv
.iter()
.map(FilePath::new)
.collect::<Result<Vec<FilePath>, _>>()?;
let fds: HashMap<u32, Fd> = fds.iter().map(|(k, val)| (*k, Fd::from(val))).collect();
self.0
.call("HostCommand", &(cwd_path, argv, fds, envs, flags))
.await
}
#[doc(alias = "SpawnSignal")]
#[doc(alias = "xdp_portal_spawn_signal")]
pub async fn host_command_signal(
&self,
pid: u32,
signal: u32,
to_process_group: bool,
) -> Result<(), Error> {
self.0
.call("HostCommandSignal", &(pid, signal, to_process_group))
.await
}
}
impl<'a> std::ops::Deref for Development<'a> {
type Target = zbus::Proxy<'a>;
fn deref(&self) -> &Self::Target {
&self.0
}
}