From 2565a53496a41135a43790fcacc12cbea0446c4a Mon Sep 17 00:00:00 2001 From: bluepython508 <16466646+bluepython508@users.noreply.github.com> Date: Sun, 20 Jul 2025 14:03:09 +0100 Subject: [PATCH] spectate command; remove spectate from ST; currently_playing improvements --- src/main.rs | 102 ++++++++++++++++++++++++++++++++++++---------------- 1 file changed, 72 insertions(+), 30 deletions(-) diff --git a/src/main.rs b/src/main.rs index f2b09e3..bb34489 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,12 +1,16 @@ use std::{future::Future, io, path::Path}; -use ::serenity::all::{ChannelId, GuildId, UserId}; +use ::serenity::all::{ChannelId, GuildId, Mentionable, UserId}; use eyre::{Context as _, Error, OptionExt, Result}; use futures::{FutureExt, StreamExt, TryStreamExt}; use poise::serenity_prelude as serenity; use rand::seq::SliceRandom; use rusqlite::OptionalExtension; -use tracing_subscriber::{fmt::{self, format::FmtSpan}, layer::SubscriberExt, EnvFilter}; +use tracing_subscriber::{ + fmt::{self, format::FmtSpan}, + layer::SubscriberExt, + EnvFilter, +}; #[derive(Copy, Clone)] struct GuildData { @@ -175,7 +179,12 @@ async fn collect( .flatten() .collect::>(); - move_users(ctx, guild, users.iter().map(|user| (to, user.user.id)).collect()).await?; + move_users( + ctx, + guild, + users.iter().map(|user| (to, user.user.id)).collect(), + ) + .await?; futures::future::try_join_all(users.iter().map(|user| guild.move_member(&ctx, user, to))) .await?; @@ -253,54 +262,86 @@ async fn join( #[poise::command(slash_command, ephemeral)] #[tracing::instrument] -async fn st(ctx: Context<'_>, mut spectators: Vec) -> Result<()> { +async fn st(ctx: Context<'_>) -> Result<()> { let guild = ctx .guild_id() .ok_or_eyre("This bot only works in servers")?; let GuildData { st, .. } = ctx.data().get(guild).await?; - spectators.push(ctx.author().id); + let sender = ctx.author().id; futures::future::try_join_all(guild.members(&ctx, None, None).await?.into_iter().map( - |member| { - let spectators = &spectators; - async move { - match ( - spectators.contains(&member.user.id), - member.roles.contains(&st), - ) { - (true, true) | (false, false) => Ok(()), - (true, false) => member.add_role(&ctx, st).await, - (false, true) => member.remove_role(&ctx, st).await, - } + |member| async move { + match (sender == member.user.id, member.roles.contains(&st)) { + (true, true) | (false, false) => Ok(()), + (true, false) => member.add_role(&ctx, st).await, + (false, true) => member.remove_role(&ctx, st).await, } }, )) .await?; - ctx.reply(format!("{} members given ST", spectators.len())) - .await?; + ctx.reply("You are now the ST").await?; Ok(()) } #[poise::command(slash_command, ephemeral)] #[tracing::instrument] -async fn currently_playing(ctx: Context<'_>, players: Vec) -> Result<()> { +async fn spectate(ctx: Context<'_>, player: Option) -> Result<()> { let guild = ctx .guild_id() .ok_or_eyre("This bot only works in servers")?; - let GuildData { - currently_playing, .. - } = ctx.data().get(guild).await?; - for player in &players { - guild - .member(&ctx, player) - .await? - .add_role(&ctx, currently_playing) - .await?; - } - ctx.reply(format!("Given {} members currently playing", players.len())) + let GuildData { st, .. } = ctx.data().get(guild).await?; + + let member = guild + .member(&ctx, player.unwrap_or(ctx.author().id)) .await?; + + let msg = if member.roles.contains(&st) { + member.remove_role(&ctx, st).await?; + "no longer a spectator" + } else { + member.add_role(&ctx, st).await?; + "now a spectator" + }; + + ctx.reply(if player.is_some() { + format!("{} is {}", member.mention(), msg) + } else { + format!("You are {}", msg) + }) + .await?; + + Ok(()) +} + +#[poise::command(slash_command, ephemeral)] +#[tracing::instrument] +async fn currently_playing(ctx: Context<'_>, player: Option) -> Result<()> { + let guild = ctx + .guild_id() + .ok_or_eyre("This bot only works in servers")?; + let GuildData { currently_playing, .. } = ctx.data().get(guild).await?; + + let member = guild + .member(&ctx, player.unwrap_or(ctx.author().id)) + .await?; + + let msg = if member.roles.contains(¤tly_playing) { + member.remove_role(&ctx, currently_playing).await?; + "no longer" + } else { + member.add_role(&ctx, currently_playing).await?; + "now" + }; + + ctx.reply(if player.is_some() { + format!("{} is {} {}", member.mention(), msg, currently_playing.mention()) + } else { + format!("You are {} {}", msg, currently_playing.mention()) + }) + .await?; + Ok(()) } @@ -382,6 +423,7 @@ async fn main() -> Result<()> { dusk(), dawn(), st(), + spectate(), currently_playing(), join(), configure(),