diff --git a/src/commands/mod.rs b/src/commands/mod.rs index 2930a52..98ea7cd 100644 --- a/src/commands/mod.rs +++ b/src/commands/mod.rs @@ -1 +1,2 @@ -pub mod moove; \ No newline at end of file +pub mod moove; +pub mod say; \ No newline at end of file diff --git a/src/commands/say.rs b/src/commands/say.rs new file mode 100644 index 0000000..c097539 --- /dev/null +++ b/src/commands/say.rs @@ -0,0 +1,17 @@ +use poise; +// use super::super::types::Data; + +type Error = Box; +type Context<'a> = poise::Context<'a, (), Error>; + +#[poise::command( + slash_command, + description_localized("en-US", "Make me say something!") +)] +pub async fn say(ctx: Context<'_>, + #[description = "What will you make me say this time? 🙃"] + message: String +) -> Result<(), Error> { + ctx.say(message).await?; + Ok(()) +} \ No newline at end of file diff --git a/src/main.rs b/src/main.rs index b4791d9..bf2381e 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,8 +1,9 @@ +use poise::samples::{register_globally, register_in_guild}; use serenity::async_trait; use serenity::prelude::GatewayIntents; use serenity::client::Context; use serenity::model::gateway::Ready; -use serenity::all::{Message, EventHandler}; +use serenity::all::{EventHandler, GuildId, Message}; use serenity::Client; use tokio_cron_scheduler::{JobScheduler, Job}; @@ -13,6 +14,8 @@ use message_handler::handle; use std::future::Future; use std::pin::Pin; +use std::sync::Arc; +use std::time::Duration; mod commands; mod util; @@ -20,8 +23,27 @@ mod util; mod other; use other::notice; +mod types; + struct Handler; +use commands::say::say; +use types::Error; + +async fn on_error(error: poise::FrameworkError<'_, (), Error>) { + match error { + poise::FrameworkError::Setup { error, .. } => panic!("Failed to start bot: {:?}", error), + poise::FrameworkError::Command { error, ctx, .. } => { + println!("Error in command `{}`: {:?}", ctx.command().name, error,); + } + error => { + if let Err(e) = poise::builtins::on_error(error).await { + println!("Error while handling error: {}", e) + } + } + } +} + #[async_trait] impl EventHandler for Handler { async fn message(&self, ctx: Context, msg: Message) { @@ -54,17 +76,51 @@ impl EventHandler for Handler { async fn main() -> anyhow::Result<()> { use anyhow::Context; + // create poise framework for registering commands + let options = poise::FrameworkOptions { + commands: vec![say()], + prefix_options: poise::PrefixFrameworkOptions { + prefix: Some("/".into()), + edit_tracker: Some(Arc::new(poise::EditTracker::for_timespan( + Duration::from_secs(3600), + ))), + ..Default::default() + }, + on_error: |err| Box::pin(on_error(err)), + command_check: Some(|ctx| { + Box::pin(async move { + return Ok(!ctx.author().bot) + }) + }), + ..Default::default() + }; + + let debug_guild_id = dotenv_var("DEBUG_GUILD_ID") + .context("DEBUG_GUILD_ID not found in env")? + .parse::().unwrap(); + + let framework = poise::Framework::builder() + .setup(move |ctx, _ready, framework| { + Box::pin(async move { + register_in_guild(ctx, &framework.options().commands, GuildId::new(debug_guild_id)).await?; + Ok(()) + }) + }) + .options(options) + .build(); + let token_str = "TOKEN"; - + #[cfg(feature="DEBUG")] let token_str = "DEBUGTOKEN"; let token = dotenv_var(token_str).context("TOKEN not found in env")?; - let intents = GatewayIntents::GUILD_MESSAGES | GatewayIntents::MESSAGE_CONTENT; + let intents = GatewayIntents::GUILD_MESSAGES | GatewayIntents::MESSAGE_CONTENT; let mut client = Client::builder(&token, intents) .event_handler(Handler) + .framework(framework) .await .context("Failed to build client")?; diff --git a/src/types.rs b/src/types.rs new file mode 100644 index 0000000..2571aab --- /dev/null +++ b/src/types.rs @@ -0,0 +1,5 @@ +// pub struct Data {} + +pub type Error = Box; +// replace () with Data if you ever need to store some additional data +// pub type Context<'a> = poise::Context<'a, (), Error>;