add ban and unban

This commit is contained in:
2025-05-17 15:04:00 -04:00
parent 8044da95e5
commit 614b912dc9
5 changed files with 117 additions and 1 deletions

View File

@@ -0,0 +1,53 @@
use crate::common::{Context, Error};
use crate::commands::settings;
use poise::serenity_prelude as serenity;
/// Ban a user
#[poise::command(slash_command, prefix_command)]
pub async fn ban(ctx: Context<'_>,
user: serenity::User,
#[rest]
reason: Option<String>) -> Result<(), Error>
{
let guild = match ctx.guild_id() {
Some(g) => g,
None => {
ctx.reply("This command must be ran within a guild.").await?;
return Ok(());
}
};
if let Some(role) = settings::get_banrole(ctx, guild).await? {
let member = guild.member(&ctx, user.id).await?;
member.add_role(ctx, &role).await?;
};
if let Some(reason) = reason {
ctx.reply(format!("{user} has been banned for {reason}.")).await?;
} else {
ctx.reply(format!("{user} has been banned.")).await?;
}
Ok(())
}
/// Unban a user
#[poise::command(slash_command, prefix_command)]
pub async fn unban(ctx: Context<'_>, user: serenity::User) -> Result<(), Error>
{
let guild = match ctx.guild_id() {
Some(g) => g,
None => {
ctx.reply("This command must be ran within a guild.").await?;
return Ok(());
}
};
if let Some(role) = settings::get_banrole(ctx, guild).await? {
let member = guild.member(&ctx, user.id).await?;
member.remove_role(ctx, &role).await?;
};
ctx.reply(format!("{user} has been unbanned.")).await?;
Ok(())
}

View File

@@ -0,0 +1 @@
pub mod ban;

View File

@@ -8,6 +8,7 @@ mod eval;
pub mod self_roles; pub mod self_roles;
mod settings; mod settings;
mod version; mod version;
mod administration;
use crate::common::{Data, Error, Context}; use crate::common::{Data, Error, Context};
@@ -38,6 +39,8 @@ pub fn commands() -> Vec<Command<Data, Error>> {
eval::eval(), eval::eval(),
self_roles::role(), self_roles::role(),
settings::setting(), settings::setting(),
administration::ban::ban(),
administration::ban::unban(),
version::version(), version::version(),
] ]
} }

View File

@@ -178,7 +178,65 @@ pub async fn hoist(ctx: Context<'_>, hoist: Option<bool>) -> Result<(), Error> {
Ok(()) Ok(())
} }
#[poise::command(prefix_command, slash_command, subcommands("prefix", "position", "hoist"), subcommand_required)] pub async fn get_banrole(ctx: Context<'_>, guild: GuildId) -> Result<Option<RoleId>, Error> {
let db = &ctx.data().database;
let role: Option<i64> = match sqlx::query("SELECT banrole FROM settings WHERE guildid = $1")
.bind(guild.get() as i64)
.fetch_one(db).await
{
Ok(r) => r.get(0),
Err(sqlx::Error::RowNotFound) => None,
Err(e) => return Err(Box::new(e)),
};
Ok(role.map(|sf| RoleId::new(sf as u64)))
}
#[poise::command(prefix_command, slash_command)]
pub async fn banrole(ctx: Context<'_>, role: Option<Role>) -> Result<(), Error> {
let guild = match ctx.guild_id() {
Some(g) => g,
None => {
ctx.reply("This command must be ran within a guild.").await?;
return Ok(());
}
};
let member = ctx.author_member().await.unwrap();
if !member.permissions(ctx).iter().any(|p| p.manage_guild()) {
ctx.reply("You do not have permission to see or change this setting.").await?;
return Ok(());
}
match role {
Some(role) => {
let mut tx = ctx.data().database.begin().await?;
sqlx::query("INSERT INTO settings (guildid, banrole) VALUES ($1, $2) ON CONFLICT (guildid) DO UPDATE SET banrole = EXCLUDED.banrole")
.bind(guild.get() as i64)
.bind(role.id.get() as i64)
.execute(&mut *tx).await?;
tx.commit().await?;
common::no_ping_reply(&ctx, format!("The bot will now give banned users the role {role}.")).await?;
}
None => {
let s = match get_banrole(ctx, guild).await? {
Some(r) => format!("{}", guild.role(ctx, r).await?),
None => "not set".into()
};
common::no_ping_reply(&ctx, format!("This server's ban role is {s}.")).await?;
}
}
Ok(())
}
#[poise::command(prefix_command, slash_command, subcommands("prefix", "position", "hoist", "banrole"), subcommand_required)]
pub async fn setting(_ctx: Context<'_>) -> Result<(), Error> { pub async fn setting(_ctx: Context<'_>) -> Result<(), Error> {
Ok(()) Ok(())
} }

View File

@@ -169,6 +169,7 @@ async fn main() -> Result<(), Error> {
CREATE TABLE IF NOT EXISTS settings ( CREATE TABLE IF NOT EXISTS settings (
guildid BIGINT NOT NULL PRIMARY KEY, guildid BIGINT NOT NULL PRIMARY KEY,
positional_role BIGINT, positional_role BIGINT,
banrole BIGINT,
hoist_selfroles BOOLEAN, hoist_selfroles BOOLEAN,
prefix TEXT prefix TEXT
) )