refactor(handlers): use teloxide's own chat-kind predicates

is_group hand-rolled what Chat::is_group/is_supergroup/is_private already
answer (verified in teloxide-core's chat.rs), and the private check was a
ChatKind pattern match. The unit test that exercised the helper asserted
teloxide's semantics; the channel case it guarded (a channel must not get the
group hint) is now asserted through handle_message instead, next to the group
case.
This commit is contained in:
2026-09-21 17:26:35 +08:00
parent d9f3ee99c1
commit 26581cfca1
+20 -47
View File
@@ -27,9 +27,7 @@ use crate::media_sender::MediaSender;
use commands::{Command, execute_command};
use teloxide::RequestError;
use teloxide::prelude::*;
use teloxide::types::{
ChatId, ChatKind, Message, MessageId, ParseMode, PublicChatKind, ReplyParameters,
};
use teloxide::types::{ChatId, Message, MessageId, ParseMode, ReplyParameters};
use teloxide::utils::command::BotCommands;
use urls::{URL_JOBS, extract_urls};
@@ -196,7 +194,7 @@ pub(crate) async fn handle_message(
bot: &Bot,
message: Message,
) -> Result<(), RequestError> {
let is_private = matches!(message.chat.kind, ChatKind::Private(_));
let is_private = message.chat.is_private();
let sender = message
.from
.as_ref()
@@ -267,7 +265,8 @@ pub(crate) async fn handle_message(
break;
}
}
} else if is_group(&message.chat.kind)
} else if message.chat.is_group()
|| message.chat.is_supergroup()
&& extract_urls(&message)
.iter()
.any(|url| x_media::site::cache_key(url).is_some())
@@ -287,18 +286,6 @@ pub(crate) async fn handle_message(
const GROUP_LINK_HINT: &str =
"Links are handled in private chat only — send me this link there, or use inline mode here.";
/// Groups and supergroups, as opposed to private chats and channels.
fn is_group(kind: &ChatKind) -> bool {
matches!(
kind,
ChatKind::Public(chat)
if matches!(
chat.kind,
PublicChatKind::Group | PublicChatKind::Supergroup(_)
)
)
}
#[cfg(test)]
mod tests {
use super::*;
@@ -464,38 +451,24 @@ mod tests {
assert_eq!(api.methods(), vec!["EditMessageCaption", "SendMessage"]);
assert_eq!(api.body("SendMessage")["text"], GROUP_LINK_HINT);
}
#[test]
fn the_link_hint_is_for_groups_only() {
use teloxide::types::{ChatPrivate, ChatPublic, PublicChatChannel, PublicChatSupergroup};
// A channel stays silent: the hint reply would be posted into the
// channel itself, so the same link must produce no further call.
let channel: Message = serde_json::from_value(serde_json::json!({
"message_id": 3,
"date": 0,
"chat": { "id": -1001234567890i64, "type": "channel", "title": "c" },
"text": "https://x.com/u/status/1",
"entities": [{ "type": "url", "offset": 0, "length": 24 }],
}))
.expect("a minimal channel message deserializes");
let group = ChatKind::Public(ChatPublic {
title: None,
kind: PublicChatKind::Group,
});
let supergroup = ChatKind::Public(ChatPublic {
title: None,
kind: PublicChatKind::Supergroup(PublicChatSupergroup {
username: None,
is_forum: false,
}),
});
// A channel must stay silent: the hint reply would be posted into the
// channel itself.
let channel = ChatKind::Public(ChatPublic {
title: None,
kind: PublicChatKind::Channel(PublicChatChannel { username: None }),
});
let private = ChatKind::Private(ChatPrivate {
username: None,
first_name: None,
last_name: None,
});
handle_message(&ctx, &bot, channel).await.unwrap();
assert!(is_group(&group));
assert!(is_group(&supergroup));
assert!(!is_group(&channel));
assert!(!is_group(&private));
assert_eq!(
api.methods(),
vec!["EditMessageCaption", "SendMessage"],
"a channel must not get the group hint"
);
}
}