mirror of
https://github.com/teloxide/teloxide.git
synced 2025-03-24 23:57:38 +01:00
updated admin_command example
This commit is contained in:
parent
9944524e34
commit
33f92f9ea0
1 changed files with 64 additions and 88 deletions
|
@ -1,4 +1,4 @@
|
||||||
// TODO: simplify this and use typed command variants (see https://github.com/teloxide/teloxide/issues/152).
|
use std::str::FromStr;
|
||||||
|
|
||||||
use teloxide::{
|
use teloxide::{
|
||||||
prelude::*, types::ChatPermissions, utils::command::BotCommand,
|
prelude::*, types::ChatPermissions, utils::command::BotCommand,
|
||||||
|
@ -18,82 +18,68 @@ use futures::future;
|
||||||
#[derive(BotCommand)]
|
#[derive(BotCommand)]
|
||||||
#[command(
|
#[command(
|
||||||
rename = "lowercase",
|
rename = "lowercase",
|
||||||
description = "Use commands in format /%command% %num% %unit%"
|
description = "Use commands in format /%command% %num% %unit%",
|
||||||
|
parse_with = "split"
|
||||||
)]
|
)]
|
||||||
enum Command {
|
enum Command {
|
||||||
#[command(description = "kick user from chat.")]
|
#[command(description = "kick user from chat.")]
|
||||||
Kick,
|
Kick,
|
||||||
#[command(description = "ban user in chat.")]
|
#[command(description = "ban user in chat.")]
|
||||||
Ban,
|
Ban {
|
||||||
|
time: u32,
|
||||||
|
unit: UnitOfTime,
|
||||||
|
},
|
||||||
#[command(description = "mute user in chat.")]
|
#[command(description = "mute user in chat.")]
|
||||||
Mute,
|
Mute {
|
||||||
|
time: u32,
|
||||||
|
unit: UnitOfTime,
|
||||||
|
},
|
||||||
Help,
|
Help,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
enum UnitOfTime {
|
||||||
|
Seconds,
|
||||||
|
Minutes,
|
||||||
|
Hours,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl FromStr for UnitOfTime {
|
||||||
|
type Err = &'static str;
|
||||||
|
fn from_str(s: &str) -> Result<Self, <Self as FromStr>::Err> {
|
||||||
|
match s {
|
||||||
|
"h" | "hours" => Ok(UnitOfTime::Hours),
|
||||||
|
"m" | "minutes" => Ok(UnitOfTime::Minutes),
|
||||||
|
"s" | "seconds" => Ok(UnitOfTime::Seconds),
|
||||||
|
_ => Err("Allowed units: h, m, s"),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Calculates time of user restriction.
|
// Calculates time of user restriction.
|
||||||
fn calc_restrict_time(num: i32, unit: &str) -> Result<i32, &str> {
|
fn calc_restrict_time(time: u32, unit: UnitOfTime) -> u32 {
|
||||||
match unit {
|
match unit {
|
||||||
"h" | "hours" => Ok(num * 3600),
|
UnitOfTime::Hours => time * 3600,
|
||||||
"m" | "minutes" => Ok(num * 60),
|
UnitOfTime::Minutes => time * 60,
|
||||||
"s" | "seconds" => Ok(num),
|
UnitOfTime::Seconds => time,
|
||||||
_ => Err("Allowed units: h, m, s"),
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Parse arguments after a command.
|
|
||||||
fn parse_args(args: &[String]) -> Result<(i32, &str), &str> {
|
|
||||||
let num = match args.get(0) {
|
|
||||||
Some(s) => s,
|
|
||||||
None => return Err("Use command in format /%command% %num% %unit%"),
|
|
||||||
};
|
|
||||||
let unit = match args.get(1) {
|
|
||||||
Some(s) => s,
|
|
||||||
None => return Err("Use command in format /%command% %num% %unit%"),
|
|
||||||
};
|
|
||||||
|
|
||||||
match num.parse::<i32>() {
|
|
||||||
Ok(n) => Ok((n, unit)),
|
|
||||||
Err(_) => Err("input positive number!"),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Parse arguments into a user restriction duration.
|
|
||||||
fn parse_time_restrict(args: &[String]) -> Result<i32, &str> {
|
|
||||||
let (num, unit) = parse_args(args)?;
|
|
||||||
calc_restrict_time(num, unit)
|
|
||||||
}
|
|
||||||
|
|
||||||
type Cx = DispatcherHandlerCx<Message>;
|
type Cx = DispatcherHandlerCx<Message>;
|
||||||
|
|
||||||
// Mute a user with a replied message.
|
// Mute a user with a replied message.
|
||||||
async fn mute_user(cx: &Cx, args: &[String]) -> ResponseResult<()> {
|
async fn mute_user(cx: &Cx, time: u32) -> ResponseResult<()> {
|
||||||
match cx.update.reply_to_message() {
|
match cx.update.reply_to_message() {
|
||||||
Some(msg1) => match parse_time_restrict(args) {
|
Some(msg1) => {
|
||||||
// Mute user temporarily...
|
cx.bot
|
||||||
Ok(time) => {
|
.restrict_chat_member(
|
||||||
cx.bot
|
cx.update.chat_id(),
|
||||||
.restrict_chat_member(
|
msg1.from().expect("Must be MessageKind::Common").id,
|
||||||
cx.update.chat_id(),
|
ChatPermissions::default(),
|
||||||
msg1.from().expect("Must be MessageKind::Common").id,
|
)
|
||||||
ChatPermissions::default(),
|
.until_date(cx.update.date + time as i32)
|
||||||
)
|
.send()
|
||||||
.until_date(cx.update.date + time)
|
.await?;
|
||||||
.send()
|
}
|
||||||
.await?;
|
|
||||||
}
|
|
||||||
// ...or permanently
|
|
||||||
Err(_) => {
|
|
||||||
cx.bot
|
|
||||||
.restrict_chat_member(
|
|
||||||
cx.update.chat_id(),
|
|
||||||
msg1.from().unwrap().id,
|
|
||||||
ChatPermissions::default(),
|
|
||||||
)
|
|
||||||
.send()
|
|
||||||
.await?;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
None => {
|
None => {
|
||||||
cx.reply_to("Use this command in reply to another message")
|
cx.reply_to("Use this command in reply to another message")
|
||||||
.send()
|
.send()
|
||||||
|
@ -123,31 +109,18 @@ async fn kick_user(cx: &Cx) -> ResponseResult<()> {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Ban a user with replied message.
|
// Ban a user with replied message.
|
||||||
async fn ban_user(cx: &Cx, args: &[String]) -> ResponseResult<()> {
|
async fn ban_user(cx: &Cx, time: u32) -> ResponseResult<()> {
|
||||||
match cx.update.reply_to_message() {
|
match cx.update.reply_to_message() {
|
||||||
Some(message) => match parse_time_restrict(args) {
|
Some(message) => {
|
||||||
// Mute user temporarily...
|
cx.bot
|
||||||
Ok(time) => {
|
.kick_chat_member(
|
||||||
cx.bot
|
cx.update.chat_id(),
|
||||||
.kick_chat_member(
|
message.from().expect("Must be MessageKind::Common").id,
|
||||||
cx.update.chat_id(),
|
)
|
||||||
message.from().expect("Must be MessageKind::Common").id,
|
.until_date(cx.update.date + time as i32)
|
||||||
)
|
.send()
|
||||||
.until_date(cx.update.date + time)
|
.await?;
|
||||||
.send()
|
}
|
||||||
.await?;
|
|
||||||
}
|
|
||||||
// ...or permanently
|
|
||||||
Err(_) => {
|
|
||||||
cx.bot
|
|
||||||
.kick_chat_member(
|
|
||||||
cx.update.chat_id(),
|
|
||||||
message.from().unwrap().id,
|
|
||||||
)
|
|
||||||
.send()
|
|
||||||
.await?;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
None => {
|
None => {
|
||||||
cx.reply_to("Use this command in a reply to another message!")
|
cx.reply_to("Use this command in a reply to another message!")
|
||||||
.send()
|
.send()
|
||||||
|
@ -160,15 +133,18 @@ async fn ban_user(cx: &Cx, args: &[String]) -> ResponseResult<()> {
|
||||||
async fn action(
|
async fn action(
|
||||||
cx: DispatcherHandlerCx<Message>,
|
cx: DispatcherHandlerCx<Message>,
|
||||||
command: Command,
|
command: Command,
|
||||||
args: &[String],
|
|
||||||
) -> ResponseResult<()> {
|
) -> ResponseResult<()> {
|
||||||
match command {
|
match command {
|
||||||
Command::Help => {
|
Command::Help => {
|
||||||
cx.answer(Command::descriptions()).send().await.map(|_| ())?
|
cx.answer(Command::descriptions()).send().await.map(|_| ())?
|
||||||
}
|
}
|
||||||
Command::Kick => kick_user(&cx).await?,
|
Command::Kick => kick_user(&cx).await?,
|
||||||
Command::Ban => ban_user(&cx, args).await?,
|
Command::Ban { time, unit } => {
|
||||||
Command::Mute => mute_user(&cx, args).await?,
|
ban_user(&cx, calc_restrict_time(time, unit)).await?
|
||||||
|
}
|
||||||
|
Command::Mute { time, unit } => {
|
||||||
|
mute_user(&cx, calc_restrict_time(time, unit)).await?
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
|
@ -181,8 +157,8 @@ async fn handle_commands(rx: DispatcherHandlerRx<Message>) {
|
||||||
// Only iterate through commands in a proper format:
|
// Only iterate through commands in a proper format:
|
||||||
.commands::<Command, &str>(panic!("Insert here your bot's name"))
|
.commands::<Command, &str>(panic!("Insert here your bot's name"))
|
||||||
// Execute all incoming commands concurrently:
|
// Execute all incoming commands concurrently:
|
||||||
.for_each_concurrent(None, |(cx, command, args)| async move {
|
.for_each_concurrent(None, |(cx, command)| async move {
|
||||||
action(cx, command, &args).await.log_on_error().await;
|
action(cx, command).await.log_on_error().await;
|
||||||
})
|
})
|
||||||
.await;
|
.await;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue