From fdfb126c9c48cb2c19d63ad23b2b0e554bb04d94 Mon Sep 17 00:00:00 2001 From: Edward Shen Date: Mon, 9 May 2022 01:37:44 -0700 Subject: [PATCH] reorg code --- src/commands/help.rs | 19 ++++++ src/commands/mod.rs | 59 +++++++++++++++++++ src/commands/ping.rs | 9 +++ src/commands/source.rs | 9 +++ src/commands/uwuify.rs | 55 ++++++++++++++++++ src/main.rs | 129 ++--------------------------------------- 6 files changed, 157 insertions(+), 123 deletions(-) create mode 100644 src/commands/help.rs create mode 100644 src/commands/mod.rs create mode 100644 src/commands/ping.rs create mode 100644 src/commands/source.rs create mode 100644 src/commands/uwuify.rs diff --git a/src/commands/help.rs b/src/commands/help.rs new file mode 100644 index 0000000..e5ad6df --- /dev/null +++ b/src/commands/help.rs @@ -0,0 +1,19 @@ +use anyhow::Result; +use enum_iterator::IntoEnumIterator; +use matrix_sdk::room::Joined; +use matrix_sdk::ruma::events::room::message::RoomMessageEventContent; + +use super::BotCommand; + +pub async fn help(room: Joined) -> Result<()> { + let mut msg = "List of commands:\n\n".to_owned(); + for command in BotCommand::into_enum_iter() { + msg.push_str(&command.to_string()); + msg.push_str(" - "); + msg.push_str(command.help_text()); + msg.push('\n'); + } + let content = RoomMessageEventContent::notice_plain(msg); + room.send(content, None).await?; + Ok(()) +} diff --git a/src/commands/mod.rs b/src/commands/mod.rs new file mode 100644 index 0000000..50a823f --- /dev/null +++ b/src/commands/mod.rs @@ -0,0 +1,59 @@ +use std::fmt::Display; +use std::str::FromStr; + +use enum_iterator::IntoEnumIterator; + +macro_rules! import_command { + ($( $command:tt ),* $(,)?) => { + $( + mod $command; + pub use $command::$command; + )* + }; +} + +import_command!(help, ping, source, uwuify); + +#[derive(IntoEnumIterator)] +pub enum BotCommand { + Help, + Source, + Uwu, + Ping, +} + +impl BotCommand { + pub const fn help_text(&self) -> &'static str { + match self { + Self::Source => "Links to the source code for this bot.", + Self::Uwu => "Uwuifies your message.", + Self::Ping => "Pong!", + Self::Help => "Prints this help.", + } + } +} + +impl FromStr for BotCommand { + type Err = (); + + fn from_str(s: &str) -> std::result::Result { + match s.to_lowercase().as_str() { + "source" => Ok(Self::Source), + "uwu" => Ok(Self::Uwu), + "ping" => Ok(Self::Ping), + "help" => Ok(Self::Help), + _ => Err(()), + } + } +} + +impl Display for BotCommand { + fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + match self { + BotCommand::Source => write!(f, "source"), + BotCommand::Uwu => write!(f, "uwu"), + BotCommand::Ping => write!(f, "ping"), + BotCommand::Help => write!(f, "help"), + } + } +} diff --git a/src/commands/ping.rs b/src/commands/ping.rs new file mode 100644 index 0000000..6a4a4ba --- /dev/null +++ b/src/commands/ping.rs @@ -0,0 +1,9 @@ +use anyhow::Result; +use matrix_sdk::room::Joined; +use matrix_sdk::ruma::events::room::message::RoomMessageEventContent; + +pub async fn ping(room: Joined) -> Result<()> { + let content = RoomMessageEventContent::text_plain("Pong!"); + room.send(content, None).await?; + Ok(()) +} diff --git a/src/commands/source.rs b/src/commands/source.rs new file mode 100644 index 0000000..b15a015 --- /dev/null +++ b/src/commands/source.rs @@ -0,0 +1,9 @@ +use anyhow::Result; +use matrix_sdk::room::Joined; +use matrix_sdk::ruma::events::room::message::RoomMessageEventContent; + +pub async fn source(room: Joined) -> Result<()> { + let content = RoomMessageEventContent::text_plain("https://git.eddie.sh/edward/matrix-bot"); + room.send(content, None).await?; + Ok(()) +} diff --git a/src/commands/uwuify.rs b/src/commands/uwuify.rs new file mode 100644 index 0000000..cc4ec18 --- /dev/null +++ b/src/commands/uwuify.rs @@ -0,0 +1,55 @@ +use anyhow::{Context, Result}; +use matrix_sdk::room::{Joined, MessagesOptions}; +use matrix_sdk::ruma::events::room::message::{ + MessageType, RoomMessageEventContent, TextMessageEventContent, +}; +use matrix_sdk::ruma::events::{ + AnyMessageLikeEvent, AnyRoomEvent, MessageLikeEvent, OriginalMessageLikeEvent, +}; +use uwuifier::uwuify_str_sse; + +pub async fn uwuify(room: Joined, message: &str) -> Result<()> { + let message = if message.is_empty() { + if let Ok(msg) = get_previous_message(&room).await { + uwuify_str_sse(&msg.body) + } else { + "uwu".to_owned() + } + } else { + uwuify_str_sse(message) + }; + let content = RoomMessageEventContent::text_plain(message); + room.send(content, None).await?; + Ok(()) +} + +async fn get_previous_message(room: &Joined) -> Result { + let last_prev_batch = (**room) + .last_prev_batch() + .context("No previous batch key while trying to find previous message")?; + let request = MessagesOptions::backward(&last_prev_batch); + let messages = room.messages(request).await?; + + messages + .chunk + .iter() + .filter_map(|msg| msg.event.deserialize().ok()) + .find_map(|msg| { + if let AnyRoomEvent::MessageLike(AnyMessageLikeEvent::RoomMessage( + MessageLikeEvent::Original(OriginalMessageLikeEvent { + content: + RoomMessageEventContent { + msgtype: MessageType::Text(content), + .. + }, + .. + }), + )) = msg + { + Some(content) + } else { + None + } + }) + .context("Failed to find previous message") +} diff --git a/src/main.rs b/src/main.rs index 82c05ab..f547c31 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,23 +1,18 @@ #![warn(clippy::nursery, clippy::pedantic)] -use std::fmt::Display; use std::path::PathBuf; use std::str::FromStr; use std::time::Duration; use anyhow::{Context, Result}; use clap::Parser; -use enum_iterator::IntoEnumIterator; use matrix_sdk::config::SyncSettings; -use matrix_sdk::room::{Joined, MessagesOptions, Room}; +use matrix_sdk::room::{Joined, Room}; use matrix_sdk::ruma::events::room::member::StrippedRoomMemberEvent; use matrix_sdk::ruma::events::room::message::{ MessageType, RoomMessageEventContent, SyncRoomMessageEvent, TextMessageEventContent, }; -use matrix_sdk::ruma::events::{ - AnyMessageLikeEvent, AnyRoomEvent, MessageLikeEvent, OriginalMessageLikeEvent, - OriginalSyncMessageLikeEvent, SyncMessageLikeEvent, -}; +use matrix_sdk::ruma::events::{OriginalSyncMessageLikeEvent, SyncMessageLikeEvent}; use matrix_sdk::ruma::OwnedUserId; use matrix_sdk::store::CryptoStore; use matrix_sdk::{Client, Session}; @@ -25,6 +20,10 @@ use serde::{Deserialize, Serialize}; use tracing::{error, info, Level}; use tracing_subscriber::util::SubscriberInitExt; +use commands::*; + +mod commands; + #[derive(Parser)] struct Args { #[clap(subcommand)] @@ -203,127 +202,11 @@ async fn parse_message(event: SyncRoomMessageEvent, room: Joined) -> Result<()> Ok(()) } -#[derive(IntoEnumIterator)] -enum BotCommand { - Help, - Source, - Uwu, - Ping, -} - -impl BotCommand { - const fn help_text(&self) -> &'static str { - match self { - Self::Source => "Links to the source code for this bot.", - Self::Uwu => "Uwuifies your message.", - Self::Ping => "Pong!", - Self::Help => "Prints this help.", - } - } -} - -impl FromStr for BotCommand { - type Err = (); - - fn from_str(s: &str) -> std::result::Result { - match s.to_lowercase().as_str() { - "source" => Ok(Self::Source), - "uwu" => Ok(Self::Uwu), - "ping" => Ok(Self::Ping), - "help" => Ok(Self::Help), - _ => Err(()), - } - } -} - -impl Display for BotCommand { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - match self { - BotCommand::Source => write!(f, "source"), - BotCommand::Uwu => write!(f, "uwu"), - BotCommand::Ping => write!(f, "ping"), - BotCommand::Help => write!(f, "help"), - } - } -} - -async fn source(room: Joined) -> Result<()> { - let content = RoomMessageEventContent::text_plain("https://git.eddie.sh/edward/matrix-bot"); - room.send(content, None).await?; - Ok(()) -} - -async fn uwuify(room: Joined, message: &str) -> Result<()> { - let message = if message.is_empty() { - if let Ok(msg) = get_previous_message(&room).await { - uwuifier::uwuify_str_sse(&msg.body) - } else { - "uwu".to_owned() - } - } else { - uwuifier::uwuify_str_sse(message) - }; - let content = RoomMessageEventContent::text_plain(message); - room.send(content, None).await?; - Ok(()) -} - -async fn get_previous_message(room: &Joined) -> Result { - let last_prev_batch = (**room) - .last_prev_batch() - .context("No previous batch key while trying to find previous message")?; - let request = MessagesOptions::backward(&last_prev_batch); - let messages = room.messages(request).await?; - - messages - .chunk - .iter() - .filter_map(|msg| msg.event.deserialize().ok()) - .find_map(|msg| { - if let AnyRoomEvent::MessageLike(AnyMessageLikeEvent::RoomMessage( - MessageLikeEvent::Original(OriginalMessageLikeEvent { - content: - RoomMessageEventContent { - msgtype: MessageType::Text(content), - .. - }, - .. - }), - )) = msg - { - Some(content) - } else { - None - } - }) - .context("Failed to find previous message") -} - -async fn ping(room: Joined) -> Result<()> { - let content = RoomMessageEventContent::text_plain("Pong!"); - room.send(content, None).await?; - Ok(()) -} - -async fn help(room: Joined) -> Result<()> { - let mut msg = "List of commands:\n\n".to_owned(); - for command in BotCommand::into_enum_iter() { - msg.push_str(&command.to_string()); - msg.push_str(" - "); - msg.push_str(command.help_text()); - msg.push('\n'); - } - let content = RoomMessageEventContent::notice_plain(msg); - room.send(content, None).await?; - Ok(()) -} - async fn unsupported_command( event: SyncRoomMessageEvent, room: Joined, command: &str, ) -> Result<()> { - // let resp = .into_full_event(room.room_id().to_owned()); let event = if let SyncRoomMessageEvent::Original(event) = event { event.into_full_event(room.room_id().to_owned()) } else {