mirror of
https://github.com/bytedance/deer-flow.git
synced 2026-09-09 21:49:37 +00:00
fix(dingtalk): strip leading mentions before command classification (#4724)
Group @bot /command messages are classified as commands like Feishu.
This commit is contained in:
parent
7b57609656
commit
e16ef2969b
@ -14,7 +14,7 @@ from typing import Any
|
||||
import httpx
|
||||
|
||||
from app.channels.base import Channel
|
||||
from app.channels.commands import is_known_channel_command
|
||||
from app.channels.commands import is_known_channel_command, strip_leading_mentions
|
||||
from app.channels.connection_identity import attach_connection_identity
|
||||
from app.channels.message_bus import InboundMessage, InboundMessageType, MessageBus, OutboundMessage, ResolvedAttachment
|
||||
from deerflow.config.paths import VIRTUAL_PATH_PREFIX, get_paths
|
||||
@ -428,8 +428,16 @@ class DingTalkChannel(Channel):
|
||||
len(files),
|
||||
)
|
||||
|
||||
if _is_dingtalk_command(text):
|
||||
# DingTalk group chats often deliver "@bot /new" with the mention left
|
||||
# in the text (Slack/Discord strip their own bot mention upstream).
|
||||
# Skip a leading mention only for the command path so ordinary chat
|
||||
# keeps @mentions intact for the agent; the stripped form also flows
|
||||
# into the inbound so ChannelManager._handle_command parses the bare
|
||||
# command. Mirrors FeishuChannel.
|
||||
command_text = strip_leading_mentions(text)
|
||||
if _is_dingtalk_command(command_text):
|
||||
msg_type = InboundMessageType.COMMAND
|
||||
text = command_text
|
||||
else:
|
||||
msg_type = InboundMessageType.CHAT
|
||||
|
||||
|
||||
@ -304,6 +304,71 @@ class TestOnChatbotMessage:
|
||||
|
||||
_run(go())
|
||||
|
||||
@pytest.mark.parametrize("text", ["@bot /new", "@_user_1 /help", "@bot /goal ship it"])
|
||||
def test_leading_mention_before_command_classifies_and_strips(self, text):
|
||||
"""DingTalk group chats leave "@bot /new" in the text; classify as COMMAND
|
||||
and strip the mention so ChannelManager receives the bare command."""
|
||||
|
||||
async def go():
|
||||
bus = MessageBus()
|
||||
bus.publish_inbound = AsyncMock()
|
||||
channel = DingTalkChannel(bus, config={})
|
||||
channel._client_id = "test_key"
|
||||
channel._main_loop = asyncio.get_event_loop()
|
||||
channel._running = True
|
||||
|
||||
msg = _make_chatbot_message(
|
||||
text=text,
|
||||
conversation_type=_CONVERSATION_TYPE_GROUP,
|
||||
sender_staff_id="user_002",
|
||||
conversation_id="conv_group_001",
|
||||
message_id="msg_mention_cmd",
|
||||
)
|
||||
|
||||
channel._send_running_reply = AsyncMock()
|
||||
channel._on_chatbot_message(msg)
|
||||
|
||||
await asyncio.sleep(0.1)
|
||||
|
||||
bus.publish_inbound.assert_awaited_once()
|
||||
inbound = bus.publish_inbound.await_args.args[0]
|
||||
assert inbound.msg_type == InboundMessageType.COMMAND, f"{text!r} should be COMMAND"
|
||||
assert not inbound.text.startswith("@"), "leading mention must be stripped for dispatch"
|
||||
assert inbound.text.split(maxsplit=1)[0] in KNOWN_CHANNEL_COMMANDS
|
||||
|
||||
_run(go())
|
||||
|
||||
def test_leading_mention_before_chat_keeps_mention(self):
|
||||
"""A mentioned non-command stays CHAT and keeps the mention for the agent."""
|
||||
|
||||
async def go():
|
||||
bus = MessageBus()
|
||||
bus.publish_inbound = AsyncMock()
|
||||
channel = DingTalkChannel(bus, config={})
|
||||
channel._client_id = "test_key"
|
||||
channel._main_loop = asyncio.get_event_loop()
|
||||
channel._running = True
|
||||
|
||||
msg = _make_chatbot_message(
|
||||
text="@bot please summarise this",
|
||||
conversation_type=_CONVERSATION_TYPE_GROUP,
|
||||
sender_staff_id="user_002",
|
||||
conversation_id="conv_group_001",
|
||||
message_id="msg_mention_chat",
|
||||
)
|
||||
|
||||
channel._send_running_reply = AsyncMock()
|
||||
channel._on_chatbot_message(msg)
|
||||
|
||||
await asyncio.sleep(0.1)
|
||||
|
||||
bus.publish_inbound.assert_awaited_once()
|
||||
inbound = bus.publish_inbound.await_args.args[0]
|
||||
assert inbound.msg_type == InboundMessageType.CHAT
|
||||
assert inbound.text == "@bot please summarise this"
|
||||
|
||||
_run(go())
|
||||
|
||||
def test_group_message_integer_conversation_type_normalized(self):
|
||||
"""SDK may deliver conversationType as int 2 — must still route as group."""
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user