This commit is contained in:
2023-03-06 12:07:56 +09:00
parent 961d4568f8
commit 5d458bf833
4 changed files with 121 additions and 100 deletions

View File

@@ -1,9 +1,9 @@
use std::{
future::{self, Future},
time::Duration, pin::Pin,
};
use std::time::Duration;
use tokio::{select, time::{sleep, Sleep}};
use tokio::{
select,
time::{sleep, Sleep},
};
use zbus::{dbus_proxy, export::ordered_stream::OrderedStreamExt, Connection, Result};
use crate::{notification::Notification, Format};

View File

@@ -1,100 +1,29 @@
use crate::notification::Hints;
use crate::notification::Notification;
use crate::notification::ServerInformation;
use std::collections::HashMap;
use zbus::dbus_interface;
use zbus::Connection;
use zbus::Result;
use zbus::SignalContext;
use zbus::fdo;
use std::{env, path::Path};
pub struct NotifyManager {
next_id: u32,
pendings: HashMap<u32, Notification>,
}
use tokio::{net::UnixListener, io::{Interest, AsyncReadExt}};
use crate::manager::NotifyManager;
impl NotifyManager {
pub fn new() -> NotifyManager {
NotifyManager {
next_id: 1,
pendings: HashMap::new(),
pub async fn listen(&self) -> Result<(), zbus::Error> {
let socket = Path::new("/tmp/fldsmdfr/socket.sock");
let listener = UnixListener::bind(socket)?;
loop {
match listener.accept().await {
Ok((stream, _addr)) => {
tokio::spawn(async move {
let ready = stream.ready(Interest::READABLE | Interest::WRITABLE).await?;
if ready.is_readable() {
let cmd = stream.read_to_string(dst)
}
});
}
Err(e) => {
eprintln!("Could not accept connection: {}", e);
}
}
}
}
pub async fn start(self) -> Result<()> {
let connection = Connection::session().await?;
connection
.object_server()
.at("/org/freedesktop/Notifications", self)
.await?;
connection
.request_name("org.freedesktop.Notifications")
.await?;
loop {}
}
}
#[dbus_interface(name = "org.freedesktop.Notifications")]
impl NotifyManager {
async fn notify(
&mut self,
#[zbus(signal_context)] ctxt: SignalContext<'_>,
app_name: String,
replaces_id: u32,
app_icon: String,
summary: String,
body: String,
actions: Vec<String>,
hints: Hints,
expire_timeout: i32,
) -> fdo::Result<u32> {
println!("{}: {}", summary, body);
let notif = Notification {
id: self.next_id,
app_name,
app_icon,
summary,
body,
actions,
hints,
};
Self::new_notification(&ctxt, &notif).await?;
self.pendings.insert(self.next_id, notif);
if replaces_id == 0 {
self.next_id += 1;
Ok(self.next_id)
} else {
Ok(replaces_id)
}
}
fn get_capabilities(&self) -> Vec<&str> {
vec![
"body",
"actions",
"body-images",
"persistence",
"icon-static",
]
}
fn get_server_information(&self) -> ServerInformation {
ServerInformation {
name: env!("CARGO_PKG_NAME").to_string(),
vendor: "zoriya".to_string(),
version: env!("CARGO_PKG_VERSION").to_string(),
spec_version: "1.2".to_string(),
}
}
#[dbus_interface(signal)]
async fn new_notification(ctxt: &SignalContext<'_>, notif: &Notification) -> Result<()>;
fn list(&self) -> Vec<&Notification> {
let mut ret: Vec<&Notification> = self.pendings.values().collect();
ret.sort_by(|a, b| a.id.cmp(&b.id));
ret
}
}

View File

@@ -1,9 +1,10 @@
mod client;
mod daemon;
mod manager;
mod notification;
use clap::{Parser, Subcommand, ValueEnum};
use daemon::NotifyManager;
use manager::NotifyManager;
use zbus::Result;
#[derive(Parser)]
@@ -52,7 +53,11 @@ async fn main() -> Result<()> {
let cli = Args::parse();
match cli.command {
Command::Daemon => NotifyManager::new().start().await,
Command::Daemon => {
let manager = NotifyManager::new();
manager.start().await?;
manager.listen().await
},
Command::List { format } => client::list(format).await,
Command::Listen { format, clear } => client::listen(format, clear).await,
}

87
src/manager.rs Normal file
View File

@@ -0,0 +1,87 @@
use crate::notification::Hints;
use crate::notification::Notification;
use crate::notification::ServerInformation;
use std::collections::HashMap;
use zbus::dbus_interface;
use zbus::Connection;
use zbus::Result;
use zbus::fdo;
pub struct NotifyManager {
next_id: u32,
pendings: HashMap<u32, Notification>,
}
impl NotifyManager {
pub fn new() -> NotifyManager {
NotifyManager {
next_id: 1,
pendings: HashMap::new(),
}
}
pub async fn start(self) -> Result<()> {
let connection = Connection::session().await?;
connection
.object_server()
.at("/org/freedesktop/Notifications", self)
.await?;
connection
.request_name("org.freedesktop.Notifications")
.await?;
Ok(())
}
}
#[dbus_interface(name = "org.freedesktop.Notifications")]
impl NotifyManager {
async fn notify(
&mut self,
app_name: String,
replaces_id: u32,
app_icon: String,
summary: String,
body: String,
actions: Vec<String>,
hints: Hints,
_expire_timeout: i32,
) -> fdo::Result<u32> {
println!("{}: {}", summary, body);
let notif = Notification {
id: self.next_id,
app_name,
app_icon,
summary,
body,
actions,
hints,
};
self.pendings.insert(self.next_id, notif);
if replaces_id == 0 {
self.next_id += 1;
Ok(self.next_id)
} else {
Ok(replaces_id)
}
}
fn get_capabilities(&self) -> Vec<&str> {
vec![
"body",
"actions",
"body-images",
"persistence",
"icon-static",
]
}
fn get_server_information(&self) -> ServerInformation {
ServerInformation {
name: env!("CARGO_PKG_NAME").to_string(),
vendor: "zoriya".to_string(),
version: env!("CARGO_PKG_VERSION").to_string(),
spec_version: "1.2".to_string(),
}
}
}