fix(qqofficial): restore @ mentions in group messages - #9705
Conversation
There was a problem hiding this comment.
Hey - I've left some high level feedback:
- Consider adding a brief inline comment near
_get_mention_idexplaining whyqq_id == 'all'is skipped, so future maintainers don’t have to rely on PR context to understand the@allbehavior limitation on QQ Official. - The new
_strip_bot_mention_markuphelper uses simplestr.replace, which will silently collapse multiple stacked mentions without preserving spacing; if multiple mentions or surrounding whitespace matter, you may want to normalize with a regex to avoid accidental concatenation of words.
Prompt for AI Agents
Please address the comments from this code review:
## Overall Comments
- Consider adding a brief inline comment near `_get_mention_id` explaining why `qq_id == 'all'` is skipped, so future maintainers don’t have to rely on PR context to understand the `@all` behavior limitation on QQ Official.
- The new `_strip_bot_mention_markup` helper uses simple `str.replace`, which will silently collapse multiple stacked mentions without preserving spacing; if multiple mentions or surrounding whitespace matter, you may want to normalize with a regex to avoid accidental concatenation of words.Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.
Sourcery review follow-upThanks for the suggestions. Addressed the review feedback:
Validation after the changes:
CI statusThe failing Latest PR run: https://github.com/AstrBotDevs/AstrBot/actions/runs/31917884276 The https://github.com/AstrBotDevs/AstrBot/actions/runs/31774429869 The matching errors include:
None of those modules are changed by this PR. The PR-specific QQ Official tests pass. |
- serialize valid At components as <@openid> markup - send mention-bearing replies and proactive messages as Markdown - preserve payload compatibility for media and guild channel messages - support legacy and current incoming mention formats - add regression tests for QQ Official @ mentions
b4ee7a6 to
6bcdf05
Compare
UpdateI updated this PR to target the current The QQ Official mention implementation and the follow-up review improvements were ported onto the current master codebase, with master-specific conflicts resolved while preserving its existing behavior. The final diff remains limited to the following three files:
Local verification completed successfully:
Unit Tests failureThe only failing test in the full suite is unrelated It fails with: AttributeError: module 'anthropic._base_client' has no attribute 'httpx'. Did you mean: 'httpx2'? This failure is caused by Anthropic SDK 1.0 renaming its private transport module from anthropic._base_client.httpx to httpx2. I have not included the unrelated Anthropic fix in th change focused and avoid duplicating #9769. |
Summary
Atcomponents as<@openid>markupThis PR is a follow-up to #9285 and its subsequent revert in #9310.
#9285 originally fixed an issue where QQ Official outgoing messages discarded
Atcomponents in_parse_to_qqofficial, causing user mentions to disappear from replies.Messages sent through
send_by_session, including proactive and scheduled group messages, were also sent through the plaincontentfield. QQ does not resolve<@openid>mentions through that path, so the mention could appear as plain text instead of an actual user mention.#9285 was later reverted by #9310 because it was reported that QQ Official did not support real mentions.
However, the QQ Bot official text-chain documentation explicitly lists mentioning users as available in group chats and text subchannels:
Official documentation:
https://bot.q.qq.com/wiki/develop/api-v2/server-inter/message/trans/text-chain.html
I reapplied the implementation to the current
devbranch and tested it in a QQ Official group-message environment. In the tested scenario, the target user was rendered as an actual mention rather than displaying the raw<@openid>markup.This PR therefore restores the behavior from #9285 while adapting it to the current codebase and preserving subsequent upstream changes.
Modifications / 改动点
qqofficial_message_event.pyto serialize validAtcomponents as<@openid>.At(qq="all"), because QQ Official group bots do not support bot-generated@allthrough this path.Atuse Markdown even when Markdown was explicitly disabled on the message chain.send_by_sessionso proactive, scheduled, and directly sent group messages containingAtusemsg_type=2with a Markdown payload.content, and switching tomsg_type=7.msg_typefield when sending messages to guild text channels.<@bot_id><@!bot_id><qqbot-at-user id="bot_id" />devchanges.At.Compatibility / 兼容性
The mention-specific behavior is only activated when a message chain contains a valid
Atcomponent, or when Markdown is explicitly requested.Ordinary messages without mentions continue to use the existing plain-text sending path.
Media messages continue to use
msg_type=7, and guild text-channel messages do not include the incompatiblemsg_typefield.Environment / 测试环境
deveede34c18360d12100f27fc2f24c8718777d237b9.9.33-52230 (64-bit)9.3.35.39800ProductionQQ Official group messageQQ Official regression tests
Test command:
Test result:
The warnings are unrelated to the mention changes:
audioopis deprecated and scheduled for removalin Python 3.13.
aiosqliteworker thread may report that the pytest event loop wasalready closed during test teardown.
Code-quality test
Test command:
Test result:
Ruff check
Command:
Result:
Ruff format
Command:
Result:
Diff check
Result:
Changed Files / 修改文件
Related / 相关 PR
45f4e666e99fa0aa95af448b7642ec84879df683Summary by Sourcery
Restore proper QQ Official group @ mention handling while keeping existing behaviors for non-mention and media/guild messages intact.
New Features:
Bug Fixes:
Enhancements:
Tests:
Summary by Sourcery
Restore reliable QQ Official @mention handling while preserving compatibility for non-mention, media, and guild messages.
New Features:
Bug Fixes:
Enhancements:
Tests: