diff --git a/.gitignore b/.gitignore index 92b1242..dad345c 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,11 @@ +# Build files /target + +# Tokens .env +# Hidden files /src/.* -.vscode +# IDE config +.vscode \ No newline at end of file diff --git a/Cargo.lock b/Cargo.lock index 5e18029..abbe157 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -17,6 +17,41 @@ version = "1.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" +[[package]] +name = "ahash" +version = "0.7.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fcb51a0695d8f838b1ee009b3fbf66bda078cd64590202a864a8f3e8c4315c47" +dependencies = [ + "getrandom", + "once_cell", + "version_check", +] + +[[package]] +name = "aho-corasick" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "43f6cb1bf222025340178f382c426f13757b2960e89779dfcb319c32542a5a41" +dependencies = [ + "memchr", +] + +[[package]] +name = "android-tzdata" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0" + +[[package]] +name = "android_system_properties" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311" +dependencies = [ + "libc", +] + [[package]] name = "anyhow" version = "1.0.71" @@ -538,10 +573,15 @@ version = "0.1.0" dependencies = [ "anyhow", "dotenv", + "mongodb", + "poise", + "rand", + "regex", "rand", "serenity", "serenity_utils", "tokio", + "url", ] [[package]] @@ -691,6 +731,35 @@ dependencies = [ "bitflags", ] +[[package]] +name = "regex" +version = "1.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "89089e897c013b3deb627116ae56a6955a72b8bed395c9526af31c9fe528b484" +dependencies = [ + "aho-corasick", + "memchr", + "regex-automata", + "regex-syntax", +] + +[[package]] +name = "regex-automata" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fa250384981ea14565685dea16a9ccc4d1c541a13f82b9c168572264d1df8c56" +dependencies = [ + "aho-corasick", + "memchr", + "regex-syntax", +] + +[[package]] +name = "regex-syntax" +version = "0.7.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2ab07dc67230e4a4718e70fd5c20055a4334b121f1f9db8fe63ef39ce9b8c846" + [[package]] name = "reqwest" version = "0.11.18" diff --git a/Cargo.toml b/Cargo.toml index 40153bc..09b7357 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -15,3 +15,6 @@ dotenv = "0.15.0" serenity = { version = "0.11.6", default-features = false, features = ["client", "gateway", "rustls_backend", "model", "http"] } serenity_utils = "0.7.0" tokio = { version = "1.29.1", features = ["macros", "rt-multi-thread"] } +rand = "0.8.4" +regex = "1.9.0" +url = "2.4.0" diff --git a/src/commands/mod.rs b/src/commands/mod.rs new file mode 100644 index 0000000..2930a52 --- /dev/null +++ b/src/commands/mod.rs @@ -0,0 +1 @@ +pub mod moove; \ No newline at end of file diff --git a/src/commands/moove.rs b/src/commands/moove.rs new file mode 100644 index 0000000..8ffff87 --- /dev/null +++ b/src/commands/moove.rs @@ -0,0 +1,74 @@ +use std::sync::Arc; +use std::time::Duration; + +use anyhow::{self, Context}; +use poise::serenity_prelude::AttachmentType; +use serenity::builder::CreateEmbed; +use serenity::http::Http; +use serenity::model::channel::Message; +use tokio::time::sleep; +use url::Url; +use regex::Regex; + +// Checks if the message should be mooved +// If the message should be mooved, try to move it and return Ok if mooved succesfully +// else returns Err() + +pub enum MooveResult { + Mooved, + NotMooveRequest +} + +pub async fn moove(http: Arc, msg: Message) -> anyhow::Result { + let word_count = msg.content.trim().split_whitespace().count(); + + let re = Regex::new(r"<#[0-9]*>$").unwrap(); + + if word_count != 1 || re.captures(&msg.content).is_none() { + return Ok(MooveResult::NotMooveRequest); + } + + let msg_to_moove = msg.clone().referenced_message.context("no message present")?; + + let mentioned_channel = http.get_channel( + msg.content[2..msg.content.len() - 1].parse::() + .unwrap()).await?.id(); + + //steals all attachments, but sets all of them as Image urls, so rip actual docs etc + let attachments = msg_to_moove + .attachments.clone() + .into_iter() + .map(|att| AttachmentType::Image(Url::parse(att.url.as_str()).unwrap())); + + //steals all the embeds + let embeds: Vec = msg_to_moove + .embeds.clone() + .into_iter() + .map(|em| CreateEmbed::from(em)) + .collect(); + + let mut new_content = format!("Sent by {}\n mooved {}\n", msg_to_moove.author, msg.author); + + if attachments.len() > 0 || embeds.len() > 0 { + new_content += format!("Message:\n{}", msg_to_moove.content).as_str(); + mentioned_channel.send_message(http.clone(), |m| { + m.content(new_content) + .add_embeds(embeds) + .add_files(attachments) + }).await?; + } + else if !msg_to_moove.content.is_empty() { + mentioned_channel.send_message(http.clone(), |m| { + m.add_embed(|e| { + e.field("MOO", new_content, false) + .field("Message:\n", msg_to_moove.content.clone(), false) + }) + }).await?; + } + + sleep(Duration::from_secs(2)).await; + + msg_to_moove.delete(http.clone()).await?; + msg.delete(http).await?; + Ok(MooveResult::Mooved) +} diff --git a/src/main.rs b/src/main.rs index 5759477..9bc6801 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,3 +1,4 @@ +use rand::random; use serenity::async_trait; use serenity::model::channel::Message; use serenity::model::gateway::Ready; @@ -5,6 +6,10 @@ use serenity::prelude::*; use util::security::dotenv_var; use other::msg::hello; +mod message_handler; +use message_handler::handle; + +mod commands; mod util; mod other; @@ -13,15 +18,34 @@ struct Handler; #[async_trait] impl EventHandler for Handler { async fn message(&self, ctx: Context, msg: Message) { - if msg.content == "!ping" { - if let Err(why) = msg.channel_id.say(&ctx.http, "Pong!").await { - println!("Error sending message: {:?}", why); - } - } + handle(ctx, msg).await; } async fn ready(&self, ctx: Context, ready: Ready) { println!("{} is connected!", ready.user.name); + let debug = match dotenv_var("DEBUG") { + Some(v) => v, + None => "OFF".to_string(), + }; + if debug != "ON" { + let messages = [ + "AAAAAAAAAAAAAAAAAAAA", + "Henlooo", + "Good day y'all!", + "May have crashed...", + "MOOOooo", + "Heyyyyy!", + "I'm baaaaack!", + "Whom'st have summoned the ancient one?", + ]; + + let rand_num = random::() % messages.len(); + let channel = ctx.http.get_channel(780439236867653635).await.unwrap().id(); + match channel.say(&ctx.http, messages[rand_num]).await { + Err(e) => println!("Something went wrong: {e}"), + Ok(_) => return, + }; + } // if ready.user.name != "MOOver Debug" { hello(ctx.http).await; // } @@ -32,15 +56,13 @@ impl EventHandler for Handler { async fn main() -> anyhow::Result<()> { use anyhow::Context; let token = dotenv_var("TOKEN").context("No TOKEN in env")?; - let intents = GatewayIntents::GUILD_MESSAGES - | GatewayIntents::DIRECT_MESSAGES - | GatewayIntents::MESSAGE_CONTENT; - + let intents = GatewayIntents::GUILD_MESSAGES | GatewayIntents::MESSAGE_CONTENT; + let mut client = Client::builder(&token, intents) .event_handler(Handler) .await .context("Failed to build client")?; - + client.start().await?; Ok(()) } diff --git a/src/message_handler.rs b/src/message_handler.rs new file mode 100644 index 0000000..391dae9 --- /dev/null +++ b/src/message_handler.rs @@ -0,0 +1,11 @@ +use serenity::client::Context; +use serenity::model::channel::Message; + +use crate::commands::moove::moove; + +pub async fn handle(ctx: Context, msg: Message) { + match moove(ctx.http, msg).await { + Ok(_) => return, + Err(e) => println!("ERROR: {e}") + }; +} \ No newline at end of file diff --git a/src/util/embeds.rs b/src/util/embeds.rs new file mode 100644 index 0000000..e69de29 diff --git a/src/util/security.rs b/src/util/security.rs index 3930652..80f2829 100644 --- a/src/util/security.rs +++ b/src/util/security.rs @@ -6,6 +6,6 @@ pub fn dotenv_var(key: &str) -> Option { match env::var(key) { Ok(val) => return Some(val), - Err(_) => None, + Err(_) => None } } \ No newline at end of file diff --git a/src/util/utilities.rs b/src/util/utilities.rs new file mode 100644 index 0000000..e69de29