block_reaction: avoid rate limits

This commit is contained in:
seth 2024-04-09 22:36:07 -04:00
parent 4795e152ca
commit 3503dda44d
No known key found for this signature in database
GPG key ID: D31BD0D494BBEE86

View file

@ -1,37 +1,34 @@
use crate::{config::Config, consts::Colors, Data}; use crate::{config::Config, consts::Colors, Data};
use chrono::Duration; use chrono::Duration;
use eyre::{Context as _, Result}; use eyre::Result;
use log::{debug, trace}; use log::{debug, trace};
use poise::serenity_prelude::{ use poise::serenity_prelude::{
Context, CreateEmbed, CreateMessage, Mentionable, Message, Reaction, Timestamp, UserId, Context, CreateEmbed, CreateMessage, Mentionable, Reaction, Timestamp,
}; };
async fn log_old_react( async fn log_old_react(ctx: &Context, config: &Config, reaction: &Reaction) -> Result<()> {
ctx: &Context,
config: &Config,
reactor: &Option<UserId>,
message: &Message,
) -> Result<()> {
let Some(log_channel) = config.discord.channels.log_channel_id else { let Some(log_channel) = config.discord.channels.log_channel_id else {
debug!("Not logging old reaction; no log channel is set!"); debug!("Not logging old reaction; no log channel is set!");
return Ok(()); return Ok(());
}; };
let message_link = reaction
.message_id
.link(reaction.channel_id, reaction.guild_id);
let mut embed = CreateEmbed::new() let mut embed = CreateEmbed::new()
.title("Old message reaction!") .title("Old message reaction!")
.color(Colors::Red); .color(Colors::Red);
if let Some(reactor) = reactor { if let Some(reactor) = reaction.user_id {
embed = embed.description(format!( embed = embed.description(format!(
"{} just reacted to {}!", "{} just reacted to {message_link}!",
reactor.mention(), reactor.mention(),
message.link()
)); ));
} else { } else {
embed = embed.description(format!( embed = embed.description(format!(
"Someone (or something...) just reacted to {}!", "Someone (or something...) just reacted to {message_link}!"
message.link()
)); ));
} }
@ -43,33 +40,25 @@ async fn log_old_react(
pub async fn handle(ctx: &Context, reaction: &Reaction, data: &Data) -> Result<()> { pub async fn handle(ctx: &Context, reaction: &Reaction, data: &Data) -> Result<()> {
let reaction_type = reaction.emoji.clone(); let reaction_type = reaction.emoji.clone();
let reactor = reaction.user_id; let message_id = reaction.message_id;
let message = reaction.message(ctx).await.wrap_err_with(|| { trace!("Checking if we should block reaction on {message_id}");
format!(
"Couldn't get message {} from reaction! We won't be able to check if it's old",
reaction.message_id
)
})?;
let time_sent = message.timestamp.to_utc(); let time_sent = message_id.created_at().to_utc();
let age = Timestamp::now().signed_duration_since(time_sent); let age = Timestamp::now().signed_duration_since(time_sent);
let max_days = Duration::days(data.config.discord.days_to_delete_reaction); let max_days = Duration::days(data.config.discord.days_to_delete_reaction);
if age >= max_days { if age >= max_days {
// NOTE: if we for some reason **didn't** get the user_id associated with the reaction,
// this will clear **all** reactions of this type. this is intentional as older reactions
// being removed > harmful reactions being kept
debug!( debug!(
"Removing reaction {reaction_type} from message {}", "Removing reaction {reaction_type} from message {}",
message.id message_id
); );
message.delete_reaction(ctx, reactor, reaction_type).await?;
log_old_react(ctx, &data.config, &reactor, &message).await?; reaction.delete(ctx).await?;
log_old_react(ctx, &data.config, reaction).await?;
} else { } else {
trace!( trace!(
"Keeping reaction {reaction_type} for message {}", "Keeping reaction {reaction_type} for message {}",
message.id message_id
); );
} }