diff --git a/xmpp/Cargo.toml b/xmpp/Cargo.toml index 81eeef6f6bcf694e47d832255151500031581a91..8d4e2c5cb5dd72cb32b26c62872219fe366e646e 100644 --- a/xmpp/Cargo.toml +++ b/xmpp/Cargo.toml @@ -16,7 +16,7 @@ edition = "2021" [dependencies] chrono = "0.4" futures = "0.3" -tokio = { version = "1", features = ["fs"] } +tokio = { version = "1", features = ["fs", "signal"] } log = "0.4" reqwest = { version = "0.12", features = ["stream"], default-features = false } tokio-util = { version = "0.7", features = ["codec"] } diff --git a/xmpp/ChangeLog b/xmpp/ChangeLog index 4dcf3ed066f434941cd3cf7817968d01c63bf3f7..dc86cf5eff8cb0c17bd06e4497dc1f39e7dc7f09 100644 --- a/xmpp/ChangeLog +++ b/xmpp/ChangeLog @@ -22,6 +22,8 @@ XXXX-YY-ZZ [ RELEASER ] Event::RoomPrivateMessageCorrection signal XEP-0308 message corrections; they're not checked how old the corrected entry is, which has security concerns (!496) - Agent::new helper method. + - Handle SIGINT, SIGTERM and SIGKILL in hello_bot example to avoid leaving + hibernating resources around. * Fixes: - Use tokio::sync::RwLock not std::sync::RwLock (!432) - Agent::wait_for_events now return Vec and sets inner tokio_xmpp Client diff --git a/xmpp/examples/hello_bot.rs b/xmpp/examples/hello_bot.rs index ba0bf66419e986bb795fb6c45f8f3539315de933..61dc2818cf728c2b5c6dbb9c27e75482cd22562d 100644 --- a/xmpp/examples/hello_bot.rs +++ b/xmpp/examples/hello_bot.rs @@ -7,9 +7,11 @@ use xmpp::{ jid::BareJid, muc::room::{JoinRoomSettings, RoomMessageSettings}, - ClientBuilder, ClientFeature, ClientType, Event, RoomNick, + Agent, ClientBuilder, ClientFeature, ClientType, Event, RoomNick, }; +use tokio::signal::ctrl_c; + use std::env::args; use std::str::FromStr; @@ -56,49 +58,64 @@ async fn main() -> Result<(), Option<()>> { log::info!("Connecting..."); loop { - for event in client.wait_for_events().await { - match event { - Event::Online => { - log::info!("Online."); - for room in &rooms { - log::info!("Joining room {} from CLI argument…", room); - client - .join_room(JoinRoomSettings { - room: room.clone(), - nick: None, - password: None, - status: Some(("en", "Yet another bot!")), - }) - .await; - } - } - Event::Disconnected(e) => { - log::info!("Disconnected: {}.", e); - } - Event::ChatMessage(_id, jid, body, time_info) => { - log::info!( - "{} {}: {}", - time_info.received.time().format("%H:%M"), - jid, - body.0 - ); - } - Event::RoomJoined(jid) => { - log::info!("Joined room {}.", jid); - client - .send_room_message(RoomMessageSettings::new(jid, "Hello world!")) - .await; - } - Event::RoomMessage(_id, jid, nick, body, time_info) => { - println!( - "Message in room {} from {} at {}: {}", - jid, nick, time_info.received, body.0 - ); - } - _ => { - log::debug!("Unimplemented event:\n{:#?}", event); + tokio::select! { + events = client.wait_for_events() => { + for event in events { + let _ = handle_events(&mut client, event, &rooms); } + }, + _ = ctrl_c() => { + log::info!("Disconnecting..."); + let _ = client.disconnect().await; + break; + }, + } + } + + Ok(()) +} + +async fn handle_events(client: &mut Agent, event: Event, rooms: &Vec) { + match event { + Event::Online => { + log::info!("Online."); + for room in rooms { + log::info!("Joining room {} from CLI argument…", room); + client + .join_room(JoinRoomSettings { + room: room.clone(), + nick: None, + password: None, + status: Some(("en", "Yet another bot!")), + }) + .await; } } + Event::Disconnected(e) => { + log::info!("Disconnected: {}.", e); + } + Event::ChatMessage(_id, jid, body, time_info) => { + log::info!( + "{} {}: {}", + time_info.received.time().format("%H:%M"), + jid, + body.0 + ); + } + Event::RoomJoined(jid) => { + log::info!("Joined room {}.", jid); + client + .send_room_message(RoomMessageSettings::new(jid, "Hello world!")) + .await; + } + Event::RoomMessage(_id, jid, nick, body, time_info) => { + println!( + "Message in room {} from {} at {}: {}", + jid, nick, time_info.received, body.0 + ); + } + _ => { + log::debug!("Unimplemented event:\n{:#?}", event); + } } }