use crate::{model::session::ChatSession, view::root::Cydonia};
use bezel::gpui::{App, SharedString, SystemNotification};
const TAG: &str = "session:";
const BODY: usize = 140;
pub fn turn_finished(chat: &ChatSession, notify: bool, cx: &mut App) {
if !notify || chat.closed || cx.active_window().is_some() {
return;
}
cx.show_system_notification(SystemNotification {
tag: SharedString::from(format!("{TAG}{}", chat.id)),
title: SharedString::from(chat.label()),
body: SharedString::from(body(chat)),
actions: Vec::new(),
});
}
pub fn session_of(tag: &str) -> Option<u64> {
tag.strip_prefix(TAG)?.parse().ok()
}
fn body(chat: &ChatSession) -> String {
use artifact::session::chat::ChatItem;
for item in chat.items.iter().rev() {
match item {
ChatItem::Notice { text, failed: true } => return clipped(text),
ChatItem::Agent(text) if !text.trim().is_empty() => return clipped(text),
_ => {}
}
}
"Finished".to_owned()
}
fn clipped(text: &str) -> String {
let line = text.trim().lines().next().unwrap_or_default().trim();
match line.char_indices().nth(BODY) {
Some((at, _)) => format!("{}…", &line[..at]),
None => line.to_owned(),
}
}
pub fn on_response(cx: &mut App) {
cx.on_system_notification_response(|response, cx| {
let Some(id) = session_of(&response.tag) else {
return;
};
cx.activate(true);
for window in cx.windows() {
let Some(window) = window.downcast::<Cydonia>() else {
continue;
};
let _ = window.update(cx, |root, _, cx| root.select_session(id, cx));
}
});
}