mirror of
https://github.com/arthur-pbty/shadowbot.git
synced 2026-06-03 23:36:25 +02:00
add invite commands
This commit is contained in:
@@ -0,0 +1,108 @@
|
|||||||
|
use serenity::builder::CreateEmbed;
|
||||||
|
use serenity::model::prelude::*;
|
||||||
|
use serenity::prelude::*;
|
||||||
|
|
||||||
|
use crate::commands::admin_common::parse_user_id;
|
||||||
|
use crate::commands::common::send_embed;
|
||||||
|
use crate::db::{DbPoolKey, add_invite_count};
|
||||||
|
|
||||||
|
pub async fn handle_addinvite(ctx: &Context, msg: &Message, args: &[&str]) {
|
||||||
|
let Some(guild_id) = msg.guild_id else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
if args.is_empty() || args.len() > 2 {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Usage: `+addinvite [@user/id] <nombre>`")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let (target_user, amount_arg) = if args.len() == 1 {
|
||||||
|
(msg.author.id, args[0])
|
||||||
|
} else {
|
||||||
|
let Some(user_id) = parse_user_id(args[0]) else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Utilisateur invalide. Utilise une mention ou un ID.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
(user_id, args[1])
|
||||||
|
};
|
||||||
|
|
||||||
|
let Ok(amount) = amount_arg.parse::<i64>() else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Le nombre doit etre un entier positif.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
if amount <= 0 {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Le nombre doit etre superieur a 0.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let Some(pool) = ({
|
||||||
|
let data = ctx.data.read().await;
|
||||||
|
data.get::<DbPoolKey>().cloned()
|
||||||
|
}) else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let bot_id = ctx.cache.current_user().id.get() as i64;
|
||||||
|
let guild_id_raw = guild_id.get() as i64;
|
||||||
|
let user_id_raw = target_user.get() as i64;
|
||||||
|
|
||||||
|
let Ok(new_total) = add_invite_count(&pool, bot_id, guild_id_raw, user_id_raw, amount).await
|
||||||
|
else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Impossible de mettre a jour les invitations.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("AddInvite")
|
||||||
|
.description(format!(
|
||||||
|
"{} invitation(s) ajoutee(s) a <@{}>.\nNouveau total: `{}`.",
|
||||||
|
amount,
|
||||||
|
target_user.get(),
|
||||||
|
new_total
|
||||||
|
))
|
||||||
|
.color(0x57F287);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct AddInviteCommand;
|
||||||
|
pub static COMMAND_DESCRIPTOR: AddInviteCommand = AddInviteCommand;
|
||||||
|
|
||||||
|
impl crate::commands::command_contract::CommandSpec for AddInviteCommand {
|
||||||
|
fn metadata(&self) -> crate::commands::command_contract::CommandMetadata {
|
||||||
|
crate::commands::command_contract::CommandMetadata {
|
||||||
|
name: "addinvite",
|
||||||
|
category: "invitation",
|
||||||
|
params: "[@membre/ID] <nombre>",
|
||||||
|
description: "Ajoute un nombre specifique d invitations a un utilisateur.",
|
||||||
|
examples: &[
|
||||||
|
"+addinvite @User 3",
|
||||||
|
"+addinvite 123456789012345678 2",
|
||||||
|
"+help addinvite",
|
||||||
|
],
|
||||||
|
default_aliases: &["ainv"],
|
||||||
|
allow_in_dm: false,
|
||||||
|
default_permission: 5,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,85 @@
|
|||||||
|
use serenity::builder::CreateEmbed;
|
||||||
|
use serenity::model::prelude::*;
|
||||||
|
use serenity::prelude::*;
|
||||||
|
|
||||||
|
use crate::commands::admin_common::parse_user_id;
|
||||||
|
use crate::commands::common::send_embed;
|
||||||
|
use crate::db::{DbPoolKey, get_invite_count};
|
||||||
|
|
||||||
|
pub async fn handle_invite(ctx: &Context, msg: &Message, args: &[&str]) {
|
||||||
|
let Some(guild_id) = msg.guild_id else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
if args.len() > 1 {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Usage: `+invite [@user/id]`")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let target_user = if args.is_empty() {
|
||||||
|
msg.author.id
|
||||||
|
} else {
|
||||||
|
let Some(user_id) = parse_user_id(args[0]) else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Utilisateur invalide. Utilise une mention ou un ID.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
user_id
|
||||||
|
};
|
||||||
|
|
||||||
|
let Some(pool) = ({
|
||||||
|
let data = ctx.data.read().await;
|
||||||
|
data.get::<DbPoolKey>().cloned()
|
||||||
|
}) else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let bot_id = ctx.cache.current_user().id.get() as i64;
|
||||||
|
let guild_id_raw = guild_id.get() as i64;
|
||||||
|
let user_id_raw = target_user.get() as i64;
|
||||||
|
|
||||||
|
let Ok(invite_count) = get_invite_count(&pool, bot_id, guild_id_raw, user_id_raw).await else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Impossible de lire le compteur d invitations.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Invite")
|
||||||
|
.description(format!(
|
||||||
|
"<@{}> a actuellement `{}` invitation(s).",
|
||||||
|
target_user.get(),
|
||||||
|
invite_count
|
||||||
|
))
|
||||||
|
.color(0x5865F2);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct InviteCommand;
|
||||||
|
pub static COMMAND_DESCRIPTOR: InviteCommand = InviteCommand;
|
||||||
|
|
||||||
|
impl crate::commands::command_contract::CommandSpec for InviteCommand {
|
||||||
|
fn metadata(&self) -> crate::commands::command_contract::CommandMetadata {
|
||||||
|
crate::commands::command_contract::CommandMetadata {
|
||||||
|
name: "invite",
|
||||||
|
category: "invitation",
|
||||||
|
params: "[@membre/ID]",
|
||||||
|
description: "Affiche le nombre d invitations d un utilisateur.",
|
||||||
|
examples: &["+invite", "+invite @User", "+help invite"],
|
||||||
|
default_aliases: &["inv"],
|
||||||
|
allow_in_dm: false,
|
||||||
|
default_permission: 0,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,73 @@
|
|||||||
|
use serenity::builder::CreateEmbed;
|
||||||
|
use serenity::model::prelude::*;
|
||||||
|
use serenity::prelude::*;
|
||||||
|
|
||||||
|
use crate::commands::common::send_embed;
|
||||||
|
use crate::db::{DbPoolKey, list_invite_board};
|
||||||
|
|
||||||
|
pub async fn handle_inviteboard(ctx: &Context, msg: &Message, _args: &[&str]) {
|
||||||
|
let Some(guild_id) = msg.guild_id else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let Some(pool) = ({
|
||||||
|
let data = ctx.data.read().await;
|
||||||
|
data.get::<DbPoolKey>().cloned()
|
||||||
|
}) else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let bot_id = ctx.cache.current_user().id.get() as i64;
|
||||||
|
let guild_id_raw = guild_id.get() as i64;
|
||||||
|
|
||||||
|
let Ok(entries) = list_invite_board(&pool, bot_id, guild_id_raw, 10).await else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Impossible de lire le classement des invitations.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
if entries.is_empty() {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("InviteBoard")
|
||||||
|
.description("Aucune invitation enregistree pour le moment.")
|
||||||
|
.color(0x5865F2);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let lines = entries
|
||||||
|
.iter()
|
||||||
|
.enumerate()
|
||||||
|
.map(|(idx, (user_id, count))| {
|
||||||
|
format!("`#{}` <@{}> - `{}` invitation(s)", idx + 1, user_id, count)
|
||||||
|
})
|
||||||
|
.collect::<Vec<_>>()
|
||||||
|
.join("\n");
|
||||||
|
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("InviteBoard")
|
||||||
|
.description(lines)
|
||||||
|
.color(0x5865F2);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct InviteBoardCommand;
|
||||||
|
pub static COMMAND_DESCRIPTOR: InviteBoardCommand = InviteBoardCommand;
|
||||||
|
|
||||||
|
impl crate::commands::command_contract::CommandSpec for InviteBoardCommand {
|
||||||
|
fn metadata(&self) -> crate::commands::command_contract::CommandMetadata {
|
||||||
|
crate::commands::command_contract::CommandMetadata {
|
||||||
|
name: "inviteboard",
|
||||||
|
category: "invitation",
|
||||||
|
params: "aucun",
|
||||||
|
description: "Affiche les 10 membres du serveur avec le plus d invitations.",
|
||||||
|
examples: &["+inviteboard", "+iboard", "+help inviteboard"],
|
||||||
|
default_aliases: &["iboard"],
|
||||||
|
allow_in_dm: false,
|
||||||
|
default_permission: 0,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,105 @@
|
|||||||
|
use serenity::builder::CreateEmbed;
|
||||||
|
use serenity::model::prelude::*;
|
||||||
|
use serenity::prelude::*;
|
||||||
|
|
||||||
|
use crate::commands::admin_common::parse_user_id;
|
||||||
|
use crate::commands::common::send_embed;
|
||||||
|
use crate::db::{DbPoolKey, reset_invite_count_for_user, reset_invite_counts_for_guild};
|
||||||
|
|
||||||
|
pub async fn handle_invitereset(ctx: &Context, msg: &Message, args: &[&str]) {
|
||||||
|
let Some(guild_id) = msg.guild_id else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
if args.len() != 1 {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Usage: `+invitereset <@user|guild>`")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let Some(pool) = ({
|
||||||
|
let data = ctx.data.read().await;
|
||||||
|
data.get::<DbPoolKey>().cloned()
|
||||||
|
}) else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let bot_id = ctx.cache.current_user().id.get() as i64;
|
||||||
|
let guild_id_raw = guild_id.get() as i64;
|
||||||
|
let target = args[0].to_lowercase();
|
||||||
|
|
||||||
|
if matches!(target.as_str(), "guild" | "serveur" | "server") {
|
||||||
|
let Ok(affected) = reset_invite_counts_for_guild(&pool, bot_id, guild_id_raw).await else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Impossible de reinitialiser les invitations du serveur.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("InviteReset")
|
||||||
|
.description(format!(
|
||||||
|
"Compteurs d invitations du serveur reinitialises. Entrees supprimees: `{}`.",
|
||||||
|
affected
|
||||||
|
))
|
||||||
|
.color(0x57F287);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let Some(user_id) = parse_user_id(args[0]) else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Cible invalide. Utilise une mention utilisateur, un ID, ou `guild`.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let Ok(_) =
|
||||||
|
reset_invite_count_for_user(&pool, bot_id, guild_id_raw, user_id.get() as i64).await
|
||||||
|
else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Impossible de reinitialiser les invitations de cet utilisateur.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("InviteReset")
|
||||||
|
.description(format!(
|
||||||
|
"Compteur d invitations reinitialise pour <@{}>.",
|
||||||
|
user_id.get()
|
||||||
|
))
|
||||||
|
.color(0x57F287);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct InviteResetCommand;
|
||||||
|
pub static COMMAND_DESCRIPTOR: InviteResetCommand = InviteResetCommand;
|
||||||
|
|
||||||
|
impl crate::commands::command_contract::CommandSpec for InviteResetCommand {
|
||||||
|
fn metadata(&self) -> crate::commands::command_contract::CommandMetadata {
|
||||||
|
crate::commands::command_contract::CommandMetadata {
|
||||||
|
name: "invitereset",
|
||||||
|
category: "invitation",
|
||||||
|
params: "<@membre/ID|guild>",
|
||||||
|
description: "Reinitialise le compteur d invitations pour un utilisateur ou le serveur.",
|
||||||
|
examples: &[
|
||||||
|
"+invitereset @User",
|
||||||
|
"+invitereset guild",
|
||||||
|
"+help invitereset",
|
||||||
|
],
|
||||||
|
default_aliases: &["invreset"],
|
||||||
|
allow_in_dm: false,
|
||||||
|
default_permission: 5,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,108 @@
|
|||||||
|
use serenity::builder::CreateEmbed;
|
||||||
|
use serenity::model::prelude::*;
|
||||||
|
use serenity::prelude::*;
|
||||||
|
|
||||||
|
use crate::commands::admin_common::parse_user_id;
|
||||||
|
use crate::commands::common::send_embed;
|
||||||
|
use crate::db::{DbPoolKey, add_invite_count};
|
||||||
|
|
||||||
|
pub async fn handle_removeinvite(ctx: &Context, msg: &Message, args: &[&str]) {
|
||||||
|
let Some(guild_id) = msg.guild_id else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
if args.is_empty() || args.len() > 2 {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Usage: `+removeinvite [@user/id] <nombre>`")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let (target_user, amount_arg) = if args.len() == 1 {
|
||||||
|
(msg.author.id, args[0])
|
||||||
|
} else {
|
||||||
|
let Some(user_id) = parse_user_id(args[0]) else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Utilisateur invalide. Utilise une mention ou un ID.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
(user_id, args[1])
|
||||||
|
};
|
||||||
|
|
||||||
|
let Ok(amount) = amount_arg.parse::<i64>() else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Le nombre doit etre un entier positif.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
if amount <= 0 {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Le nombre doit etre superieur a 0.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let Some(pool) = ({
|
||||||
|
let data = ctx.data.read().await;
|
||||||
|
data.get::<DbPoolKey>().cloned()
|
||||||
|
}) else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let bot_id = ctx.cache.current_user().id.get() as i64;
|
||||||
|
let guild_id_raw = guild_id.get() as i64;
|
||||||
|
let user_id_raw = target_user.get() as i64;
|
||||||
|
|
||||||
|
let Ok(new_total) = add_invite_count(&pool, bot_id, guild_id_raw, user_id_raw, -amount).await
|
||||||
|
else {
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("Erreur")
|
||||||
|
.description("Impossible de mettre a jour les invitations.")
|
||||||
|
.color(0xED4245);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
let embed = CreateEmbed::new()
|
||||||
|
.title("RemoveInvite")
|
||||||
|
.description(format!(
|
||||||
|
"{} invitation(s) retiree(s) a <@{}>.\nNouveau total: `{}`.",
|
||||||
|
amount,
|
||||||
|
target_user.get(),
|
||||||
|
new_total
|
||||||
|
))
|
||||||
|
.color(0x57F287);
|
||||||
|
send_embed(ctx, msg, embed).await;
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct RemoveInviteCommand;
|
||||||
|
pub static COMMAND_DESCRIPTOR: RemoveInviteCommand = RemoveInviteCommand;
|
||||||
|
|
||||||
|
impl crate::commands::command_contract::CommandSpec for RemoveInviteCommand {
|
||||||
|
fn metadata(&self) -> crate::commands::command_contract::CommandMetadata {
|
||||||
|
crate::commands::command_contract::CommandMetadata {
|
||||||
|
name: "removeinvite",
|
||||||
|
category: "invitation",
|
||||||
|
params: "[@membre/ID] <nombre>",
|
||||||
|
description: "Retire un nombre specifique d invitations a un utilisateur.",
|
||||||
|
examples: &[
|
||||||
|
"+removeinvite @User 1",
|
||||||
|
"+removeinvite 123456789012345678 2",
|
||||||
|
"+help removeinvite",
|
||||||
|
],
|
||||||
|
default_aliases: &["rinv"],
|
||||||
|
allow_in_dm: false,
|
||||||
|
default_permission: 5,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+14
-2
@@ -1,5 +1,7 @@
|
|||||||
use crate::commands::command_contract::{CommandMetadata, CommandSpec};
|
use crate::commands::command_contract::{CommandMetadata, CommandSpec};
|
||||||
|
|
||||||
|
#[path = "invitation/addinvite.rs"]
|
||||||
|
pub mod addinvite;
|
||||||
#[path = "roles/addrole.rs"]
|
#[path = "roles/addrole.rs"]
|
||||||
pub mod addrole;
|
pub mod addrole;
|
||||||
#[path = "../utils/admin_common.rs"]
|
#[path = "../utils/admin_common.rs"]
|
||||||
@@ -150,8 +152,12 @@ pub mod hideall;
|
|||||||
pub mod idle;
|
pub mod idle;
|
||||||
#[path = "botconfig/invisible.rs"]
|
#[path = "botconfig/invisible.rs"]
|
||||||
pub mod invisible;
|
pub mod invisible;
|
||||||
#[path = "owner/invite.rs"]
|
#[path = "invitation/invite.rs"]
|
||||||
pub mod invite;
|
pub mod invite;
|
||||||
|
#[path = "invitation/inviteboard.rs"]
|
||||||
|
pub mod inviteboard;
|
||||||
|
#[path = "invitation/invitereset.rs"]
|
||||||
|
pub mod invitereset;
|
||||||
#[path = "config/join.rs"]
|
#[path = "config/join.rs"]
|
||||||
pub mod join;
|
pub mod join;
|
||||||
#[path = "mod/kick.rs"]
|
#[path = "mod/kick.rs"]
|
||||||
@@ -252,6 +258,8 @@ pub mod punishsetup;
|
|||||||
pub mod raidlog;
|
pub mod raidlog;
|
||||||
#[path = "botconfig/removeactivity.rs"]
|
#[path = "botconfig/removeactivity.rs"]
|
||||||
pub mod remove_activity;
|
pub mod remove_activity;
|
||||||
|
#[path = "invitation/removeinvite.rs"]
|
||||||
|
pub mod removeinvite;
|
||||||
#[path = "ticket/rename.rs"]
|
#[path = "ticket/rename.rs"]
|
||||||
pub mod rename;
|
pub mod rename;
|
||||||
#[path = "channel/renew.rs"]
|
#[path = "channel/renew.rs"]
|
||||||
@@ -390,6 +398,11 @@ pub mod watch;
|
|||||||
pub fn all_command_metadata() -> Vec<CommandMetadata> {
|
pub fn all_command_metadata() -> Vec<CommandMetadata> {
|
||||||
vec![
|
vec![
|
||||||
ping::COMMAND_DESCRIPTOR.metadata(),
|
ping::COMMAND_DESCRIPTOR.metadata(),
|
||||||
|
addinvite::COMMAND_DESCRIPTOR.metadata(),
|
||||||
|
invite::COMMAND_DESCRIPTOR.metadata(),
|
||||||
|
inviteboard::COMMAND_DESCRIPTOR.metadata(),
|
||||||
|
invitereset::COMMAND_DESCRIPTOR.metadata(),
|
||||||
|
removeinvite::COMMAND_DESCRIPTOR.metadata(),
|
||||||
timeout::COMMAND_DESCRIPTOR.metadata(),
|
timeout::COMMAND_DESCRIPTOR.metadata(),
|
||||||
allbots::COMMAND_DESCRIPTOR.metadata(),
|
allbots::COMMAND_DESCRIPTOR.metadata(),
|
||||||
alladmins::COMMAND_DESCRIPTOR.metadata(),
|
alladmins::COMMAND_DESCRIPTOR.metadata(),
|
||||||
@@ -559,7 +572,6 @@ pub fn all_command_metadata() -> Vec<CommandMetadata> {
|
|||||||
mpsettings::COMMAND_DESCRIPTOR.metadata(),
|
mpsettings::COMMAND_DESCRIPTOR.metadata(),
|
||||||
mpsent::COMMAND_DESCRIPTOR.metadata(),
|
mpsent::COMMAND_DESCRIPTOR.metadata(),
|
||||||
mpdelete::COMMAND_DESCRIPTOR.metadata(),
|
mpdelete::COMMAND_DESCRIPTOR.metadata(),
|
||||||
invite::COMMAND_DESCRIPTOR.metadata(),
|
|
||||||
leave::COMMAND_DESCRIPTOR.metadata(),
|
leave::COMMAND_DESCRIPTOR.metadata(),
|
||||||
leave_settings::COMMAND_DESCRIPTOR.metadata(),
|
leave_settings::COMMAND_DESCRIPTOR.metadata(),
|
||||||
viewlogs::COMMAND_DESCRIPTOR.metadata(),
|
viewlogs::COMMAND_DESCRIPTOR.metadata(),
|
||||||
|
|||||||
@@ -86,6 +86,11 @@ const HELP_PAGES: &[HelpPage] = &[
|
|||||||
title: "Infos",
|
title: "Infos",
|
||||||
description: "Informations sur le serveur, les membres et les profils.",
|
description: "Informations sur le serveur, les membres et les profils.",
|
||||||
},
|
},
|
||||||
|
HelpPage {
|
||||||
|
key: "invitation",
|
||||||
|
title: "Invitation",
|
||||||
|
description: "Compteurs d invitations et classement des invitations du serveur.",
|
||||||
|
},
|
||||||
HelpPage {
|
HelpPage {
|
||||||
key: "logs",
|
key: "logs",
|
||||||
title: "Logs",
|
title: "Logs",
|
||||||
@@ -132,6 +137,7 @@ fn help_page_for_command(
|
|||||||
meta: &crate::commands::command_contract::CommandMetadata,
|
meta: &crate::commands::command_contract::CommandMetadata,
|
||||||
) -> &'static str {
|
) -> &'static str {
|
||||||
match meta.name {
|
match meta.name {
|
||||||
|
"addinvite" | "removeinvite" | "invite" | "invitereset" | "inviteboard" => "invitation",
|
||||||
"modlog" | "messagelog" | "voicelog" | "boostlog" | "rolelog" | "raidlog"
|
"modlog" | "messagelog" | "voicelog" | "boostlog" | "rolelog" | "raidlog"
|
||||||
| "autoconfiglog" | "nolog" | "joinsettings" | "boostembed" | "setmodlogs"
|
| "autoconfiglog" | "nolog" | "joinsettings" | "boostembed" | "setmodlogs"
|
||||||
| "setboostembed" | "leavesettings" | "viewlogs" => "logs",
|
| "setboostembed" | "leavesettings" | "viewlogs" => "logs",
|
||||||
@@ -151,12 +157,13 @@ fn help_page_for_command(
|
|||||||
| "idle" | "dnd" | "invisible" | "change" | "changereset" | "changeall" => "bot",
|
| "idle" | "dnd" | "invisible" | "change" | "changereset" | "changeall" => "bot",
|
||||||
"owner" | "unowner" | "clearowners" | "bl" | "unbl" | "blinfo" | "clearbl" | "allbots"
|
"owner" | "unowner" | "clearowners" | "bl" | "unbl" | "blinfo" | "clearbl" | "allbots"
|
||||||
| "alladmins" | "botadmins" | "mainprefix" | "prefix" | "mp" | "mpsettings" | "mpsent"
|
| "alladmins" | "botadmins" | "mainprefix" | "prefix" | "mp" | "mpsettings" | "mpsent"
|
||||||
| "mpdelete" | "invite" | "leave" | "discussion" => "administration",
|
| "mpdelete" | "leave" | "discussion" => "administration",
|
||||||
"perms" | "delperm" | "clearperms" | "allperms" | "alias" | "help" | "helpsetting" => {
|
"perms" | "delperm" | "clearperms" | "allperms" | "alias" | "help" | "helpsetting" => {
|
||||||
"permissions"
|
"permissions"
|
||||||
}
|
}
|
||||||
_ => match meta.category {
|
_ => match meta.category {
|
||||||
"info" => "infos",
|
"info" => "infos",
|
||||||
|
"invitation" => "invitation",
|
||||||
"mod" => "moderation",
|
"mod" => "moderation",
|
||||||
"config" => "logs",
|
"config" => "logs",
|
||||||
"botconfig" => "bot",
|
"botconfig" => "bot",
|
||||||
@@ -219,6 +226,13 @@ fn help_page_matches_input(page: &HelpPage, input: &str) -> bool {
|
|||||||
let normalized = help_lookup_key(input);
|
let normalized = help_lookup_key(input);
|
||||||
let aliases = match page.key {
|
let aliases = match page.key {
|
||||||
"infos" => &["general", "info", "informations"][..],
|
"infos" => &["general", "info", "informations"][..],
|
||||||
|
"invitation" => &[
|
||||||
|
"invite",
|
||||||
|
"invites",
|
||||||
|
"invitation",
|
||||||
|
"invitations",
|
||||||
|
"inviteboard",
|
||||||
|
][..],
|
||||||
"logs" => &["log", "journal"][..],
|
"logs" => &["log", "journal"][..],
|
||||||
"moderation" => &["mod", "sanction"][..],
|
"moderation" => &["mod", "sanction"][..],
|
||||||
"roles" => &["role", "roles"][..],
|
"roles" => &["role", "roles"][..],
|
||||||
@@ -424,6 +438,10 @@ fn help_lookup_to_key(input: &str) -> Option<&'static str> {
|
|||||||
"mpsettings" => Some("mpsettings"),
|
"mpsettings" => Some("mpsettings"),
|
||||||
"mpsent" => Some("mpsent"),
|
"mpsent" => Some("mpsent"),
|
||||||
"mpdelete" | "mpdel" => Some("mpdelete"),
|
"mpdelete" | "mpdel" => Some("mpdelete"),
|
||||||
|
"add invite" | "addinvite" => Some("addinvite"),
|
||||||
|
"remove invite" | "removeinvite" => Some("removeinvite"),
|
||||||
|
"invite reset" | "invitereset" => Some("invitereset"),
|
||||||
|
"invite board" | "inviteboard" => Some("inviteboard"),
|
||||||
"discussion" => Some("discussion"),
|
"discussion" => Some("discussion"),
|
||||||
"owner" => Some("owner"),
|
"owner" => Some("owner"),
|
||||||
"unowner" => Some("unowner"),
|
"unowner" => Some("unowner"),
|
||||||
|
|||||||
@@ -184,6 +184,16 @@ pub struct TempvocProfile {
|
|||||||
pub updated_at: DateTime<Utc>,
|
pub updated_at: DateTime<Utc>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone, sqlx::FromRow)]
|
||||||
|
#[allow(dead_code)]
|
||||||
|
pub struct InviteCounter {
|
||||||
|
pub bot_id: i64,
|
||||||
|
pub guild_id: i64,
|
||||||
|
pub user_id: i64,
|
||||||
|
pub invite_count: i64,
|
||||||
|
pub updated_at: DateTime<Utc>,
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone, sqlx::FromRow)]
|
#[derive(Debug, Clone, sqlx::FromRow)]
|
||||||
#[allow(dead_code)]
|
#[allow(dead_code)]
|
||||||
pub struct ModerationSettings {
|
pub struct ModerationSettings {
|
||||||
@@ -906,6 +916,30 @@ pub async fn init_schema(pool: &PgPool) -> Result<(), sqlx::Error> {
|
|||||||
.execute(pool)
|
.execute(pool)
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
|
sqlx::query(
|
||||||
|
r#"
|
||||||
|
CREATE TABLE IF NOT EXISTS bot_invite_counts (
|
||||||
|
bot_id BIGINT NOT NULL,
|
||||||
|
guild_id BIGINT NOT NULL,
|
||||||
|
user_id BIGINT NOT NULL,
|
||||||
|
invite_count BIGINT NOT NULL DEFAULT 0,
|
||||||
|
updated_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),
|
||||||
|
PRIMARY KEY (bot_id, guild_id, user_id)
|
||||||
|
);
|
||||||
|
"#,
|
||||||
|
)
|
||||||
|
.execute(pool)
|
||||||
|
.await?;
|
||||||
|
|
||||||
|
sqlx::query(
|
||||||
|
r#"
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_bot_invite_counts_lookup
|
||||||
|
ON bot_invite_counts (bot_id, guild_id, invite_count DESC, updated_at ASC);
|
||||||
|
"#,
|
||||||
|
)
|
||||||
|
.execute(pool)
|
||||||
|
.await?;
|
||||||
|
|
||||||
sqlx::query(
|
sqlx::query(
|
||||||
r#"
|
r#"
|
||||||
CREATE TABLE IF NOT EXISTS bot_tempvoc_settings (
|
CREATE TABLE IF NOT EXISTS bot_tempvoc_settings (
|
||||||
@@ -3240,6 +3274,123 @@ pub async fn is_piconly_channel(
|
|||||||
Ok(row.0)
|
Ok(row.0)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ========== INVITE COUNTERS FUNCTIONS ==========
|
||||||
|
|
||||||
|
pub async fn get_invite_count(
|
||||||
|
pool: &PgPool,
|
||||||
|
bot_id: i64,
|
||||||
|
guild_id: i64,
|
||||||
|
user_id: i64,
|
||||||
|
) -> Result<i64, sqlx::Error> {
|
||||||
|
let row = sqlx::query_as::<_, (i64,)>(
|
||||||
|
r#"
|
||||||
|
SELECT invite_count
|
||||||
|
FROM bot_invite_counts
|
||||||
|
WHERE bot_id = $1 AND guild_id = $2 AND user_id = $3;
|
||||||
|
"#,
|
||||||
|
)
|
||||||
|
.bind(bot_id)
|
||||||
|
.bind(guild_id)
|
||||||
|
.bind(user_id)
|
||||||
|
.fetch_optional(pool)
|
||||||
|
.await?;
|
||||||
|
|
||||||
|
Ok(row.map(|value| value.0).unwrap_or(0))
|
||||||
|
}
|
||||||
|
|
||||||
|
pub async fn add_invite_count(
|
||||||
|
pool: &PgPool,
|
||||||
|
bot_id: i64,
|
||||||
|
guild_id: i64,
|
||||||
|
user_id: i64,
|
||||||
|
delta: i64,
|
||||||
|
) -> Result<i64, sqlx::Error> {
|
||||||
|
let row = sqlx::query_as::<_, (i64,)>(
|
||||||
|
r#"
|
||||||
|
INSERT INTO bot_invite_counts (bot_id, guild_id, user_id, invite_count)
|
||||||
|
VALUES ($1, $2, $3, GREATEST($4, 0))
|
||||||
|
ON CONFLICT (bot_id, guild_id, user_id)
|
||||||
|
DO UPDATE SET
|
||||||
|
invite_count = GREATEST(bot_invite_counts.invite_count + $4, 0),
|
||||||
|
updated_at = NOW()
|
||||||
|
RETURNING invite_count;
|
||||||
|
"#,
|
||||||
|
)
|
||||||
|
.bind(bot_id)
|
||||||
|
.bind(guild_id)
|
||||||
|
.bind(user_id)
|
||||||
|
.bind(delta)
|
||||||
|
.fetch_one(pool)
|
||||||
|
.await?;
|
||||||
|
|
||||||
|
Ok(row.0)
|
||||||
|
}
|
||||||
|
|
||||||
|
pub async fn reset_invite_count_for_user(
|
||||||
|
pool: &PgPool,
|
||||||
|
bot_id: i64,
|
||||||
|
guild_id: i64,
|
||||||
|
user_id: i64,
|
||||||
|
) -> Result<u64, sqlx::Error> {
|
||||||
|
let result = sqlx::query(
|
||||||
|
r#"
|
||||||
|
DELETE FROM bot_invite_counts
|
||||||
|
WHERE bot_id = $1 AND guild_id = $2 AND user_id = $3;
|
||||||
|
"#,
|
||||||
|
)
|
||||||
|
.bind(bot_id)
|
||||||
|
.bind(guild_id)
|
||||||
|
.bind(user_id)
|
||||||
|
.execute(pool)
|
||||||
|
.await?;
|
||||||
|
|
||||||
|
Ok(result.rows_affected())
|
||||||
|
}
|
||||||
|
|
||||||
|
pub async fn reset_invite_counts_for_guild(
|
||||||
|
pool: &PgPool,
|
||||||
|
bot_id: i64,
|
||||||
|
guild_id: i64,
|
||||||
|
) -> Result<u64, sqlx::Error> {
|
||||||
|
let result = sqlx::query(
|
||||||
|
r#"
|
||||||
|
DELETE FROM bot_invite_counts
|
||||||
|
WHERE bot_id = $1 AND guild_id = $2;
|
||||||
|
"#,
|
||||||
|
)
|
||||||
|
.bind(bot_id)
|
||||||
|
.bind(guild_id)
|
||||||
|
.execute(pool)
|
||||||
|
.await?;
|
||||||
|
|
||||||
|
Ok(result.rows_affected())
|
||||||
|
}
|
||||||
|
|
||||||
|
pub async fn list_invite_board(
|
||||||
|
pool: &PgPool,
|
||||||
|
bot_id: i64,
|
||||||
|
guild_id: i64,
|
||||||
|
limit: i64,
|
||||||
|
) -> Result<Vec<(i64, i64)>, sqlx::Error> {
|
||||||
|
let capped_limit = limit.clamp(1, 100);
|
||||||
|
let rows = sqlx::query_as::<_, (i64, i64)>(
|
||||||
|
r#"
|
||||||
|
SELECT user_id, invite_count
|
||||||
|
FROM bot_invite_counts
|
||||||
|
WHERE bot_id = $1 AND guild_id = $2 AND invite_count > 0
|
||||||
|
ORDER BY invite_count DESC, updated_at ASC
|
||||||
|
LIMIT $3;
|
||||||
|
"#,
|
||||||
|
)
|
||||||
|
.bind(bot_id)
|
||||||
|
.bind(guild_id)
|
||||||
|
.bind(capped_limit)
|
||||||
|
.fetch_all(pool)
|
||||||
|
.await?;
|
||||||
|
|
||||||
|
Ok(rows)
|
||||||
|
}
|
||||||
|
|
||||||
// ========== ANCIEN SETTINGS FUNCTIONS ==========
|
// ========== ANCIEN SETTINGS FUNCTIONS ==========
|
||||||
|
|
||||||
pub async fn get_or_create_old_member_settings(
|
pub async fn get_or_create_old_member_settings(
|
||||||
|
|||||||
+23
-19
@@ -6,25 +6,25 @@ use std::sync::{Mutex, OnceLock};
|
|||||||
use crate::commands::moderation_tools;
|
use crate::commands::moderation_tools;
|
||||||
use crate::commands::remove_activity;
|
use crate::commands::remove_activity;
|
||||||
use crate::commands::{
|
use crate::commands::{
|
||||||
addrole, alias, ancien, antilink, antimassmention, antiraideautoconfig, antispam, autobackup,
|
addinvite, addrole, alias, ancien, antilink, antimassmention, antiraideautoconfig, antispam,
|
||||||
autoconfiglog, autopublish, autopublishoff, autopublishon, autoreact, backup, badwords, ban,
|
autobackup, autoconfiglog, autopublish, autopublishoff, autopublishon, autoreact, backup,
|
||||||
banlist, banner, bl, blinfo, boostembed, boosters, boostlog, bringall, button, calc, change,
|
badwords, ban, banlist, banner, bl, blinfo, boostembed, boosters, boostlog, bringall, button,
|
||||||
changeall, changereset, channel, choose, claim, cleanup, clear_all_sanctions, clear_badwords,
|
calc, change, changeall, changereset, channel, choose, claim, cleanup, clear_all_sanctions,
|
||||||
clear_bl, clear_limit, clear_messages, clear_owners, clear_perms, clear_sanctions, close,
|
clear_badwords, clear_bl, clear_limit, clear_messages, clear_owners, clear_perms,
|
||||||
cmute, compet, create, del_sanction, delperm, delrole, derank, discussion, dnd, embed, emoji,
|
clear_sanctions, close, cmute, compet, create, del_sanction, delperm, delrole, derank,
|
||||||
end, endgiveaway, giveaway, help, helpsetting, hide, hideall, idle, invisible, invite, join,
|
discussion, dnd, embed, emoji, end, endgiveaway, giveaway, help, helpsetting, hide, hideall,
|
||||||
kick, leave, leave_settings, link, listen, loading, lock, lockall, mainprefix, massiverole,
|
idle, invisible, invite, inviteboard, invitereset, join, kick, leave, leave_settings, link,
|
||||||
member, messagelog, modlog, mp, mpdelete, mpsent, mpsettings, mute, mutelist, muterole,
|
listen, loading, lock, lockall, mainprefix, massiverole, member, messagelog, modlog, mp,
|
||||||
newsticker, noderank, noderankadd, noderankdel, nolog, online, owner, perms, pic, piconly,
|
mpdelete, mpsent, mpsettings, mute, mutelist, muterole, newsticker, noderank, noderankadd,
|
||||||
piconlyadd, piconlydel, ping, playto, prefix, public, punish, punishadd, punishdel,
|
noderankdel, nolog, online, owner, perms, pic, piconly, piconlyadd, piconlydel, ping, playto,
|
||||||
punishsetup, raidlog, rename, renew, reroll, resetantiraide, role, rolelog, rolemembers,
|
prefix, public, punish, punishadd, punishdel, punishsetup, raidlog, removeinvite, rename,
|
||||||
rolemenu, sanctions, say, serverbanner, serverinfo, serverlist, serverpic, set_boostembed,
|
renew, reroll, resetantiraide, role, rolelog, rolemembers, rolemenu, sanctions, say,
|
||||||
set_modlogs, set_muterole, setbanner, setname, setperm, setpic, setprofil, shadowbot, showpics,
|
serverbanner, serverinfo, serverlist, serverpic, set_boostembed, set_modlogs, set_muterole,
|
||||||
slowmode, snipe, spam, stream, strikes, suggestion, suggestionsettings, sync, tempban,
|
setbanner, setname, setperm, setpic, setprofil, shadowbot, showpics, slowmode, snipe, spam,
|
||||||
tempcmute, tempmute, temprole, tempvoc, tempvoc_cmd, theme, ticket, ticket_member, tickets,
|
stream, strikes, suggestion, suggestionsettings, sync, tempban, tempcmute, tempmute, temprole,
|
||||||
timeout, unalias, unban, unbanall, unbl, uncmute, unhide, unhideall, unlock, unlockall,
|
tempvoc, tempvoc_cmd, theme, ticket, ticket_member, tickets, timeout, unalias, unban, unbanall,
|
||||||
unmassiverole, unmute, unmuteall, unowner, untemprole, user, viewlogs, vocinfo, voicekick,
|
unbl, uncmute, unhide, unhideall, unlock, unlockall, unmassiverole, unmute, unmuteall, unowner,
|
||||||
voicelog, voicemove, warn, watch,
|
untemprole, user, viewlogs, vocinfo, voicekick, voicelog, voicemove, warn, watch,
|
||||||
};
|
};
|
||||||
use crate::commands::{alladmins, allbots, allperms, botadmins};
|
use crate::commands::{alladmins, allbots, allperms, botadmins};
|
||||||
use crate::db::{DbPoolKey, upsert_message_observed};
|
use crate::db::{DbPoolKey, upsert_message_observed};
|
||||||
@@ -418,7 +418,11 @@ pub async fn handle_message(ctx: &Context, msg: &Message) {
|
|||||||
"mpsent" => mpsent::handle_mpsent_command(ctx, msg, &args).await,
|
"mpsent" => mpsent::handle_mpsent_command(ctx, msg, &args).await,
|
||||||
"mpdelete" | "mpdel" => mpdelete::handle_mpdelete_command(ctx, msg, &args).await,
|
"mpdelete" | "mpdel" => mpdelete::handle_mpdelete_command(ctx, msg, &args).await,
|
||||||
"mp" => mp::handle_mp(ctx, msg, &args).await,
|
"mp" => mp::handle_mp(ctx, msg, &args).await,
|
||||||
|
"addinvite" => addinvite::handle_addinvite(ctx, msg, &args).await,
|
||||||
"invite" => invite::handle_invite(ctx, msg, &args).await,
|
"invite" => invite::handle_invite(ctx, msg, &args).await,
|
||||||
|
"removeinvite" => removeinvite::handle_removeinvite(ctx, msg, &args).await,
|
||||||
|
"invitereset" => invitereset::handle_invitereset(ctx, msg, &args).await,
|
||||||
|
"inviteboard" => inviteboard::handle_inviteboard(ctx, msg, &args).await,
|
||||||
"leavesettings" => leave_settings::handle_leave_settings(ctx, msg, &args).await,
|
"leavesettings" => leave_settings::handle_leave_settings(ctx, msg, &args).await,
|
||||||
"leave" => leave::handle_leave(ctx, msg, &args).await,
|
"leave" => leave::handle_leave(ctx, msg, &args).await,
|
||||||
"viewlogs" => viewlogs::handle_viewlogs(ctx, msg, &args).await,
|
"viewlogs" => viewlogs::handle_viewlogs(ctx, msg, &args).await,
|
||||||
|
|||||||
Reference in New Issue
Block a user