feat(chat): 实现并发消息处理系统

引入了一个全新的并发消息处理系统,以显著提升在高活跃度群聊中的响应速度。

在此之前,消息管理器对每个聊天流(如一个群聊)内的所有消息进行串行处理,导致用户需要排队等待机器人响应。新系统引入了可配置的并发模式:

- 通过 `concurrent_message_processing` 开关启用。
- 允许并行处理来自同一群聊中不同用户的消息。
- 通过 `process_by_user_id` 保证对同一用户的消息处理仍然是串行的,以维持上下文的连贯性。
- 使用 `concurrent_per_user_limit` 控制并发处理的用户数量。

为了支持此功能,对 `MessageManager` 进行了大规模重构,用更高效的独立流检查机制取代了旧的全局轮询和优先级排序逻辑。同时,清理和移除了大量已废弃或冗余的配置项,简化了整体配置。

BREAKING CHANGE: 移除了多个已废弃的 `ChatConfig` 配置项,包括 `mentioned_bot_inevitable_reply`, `at_bot_inevitable_reply`, `focus_value`, `group_chat_mode` 等。这些功能已被新的 AFC 逻辑或其它机制取代。请参考最新的配置文件模板进行更新。
This commit is contained in:
tt-P607
2025-09-26 00:24:34 +08:00
committed by Windpicker-owo
parent 66f9b9b84f
commit 0beb62421c
7 changed files with 273 additions and 433 deletions

View File

@@ -53,12 +53,13 @@ class AffinityChatter(BaseChatter):
}
self.last_activity_time = time.time()
async def execute(self, context: StreamContext) -> dict:
async def execute(self, context: StreamContext, unread_messages: list | None = None) -> dict:
"""
处理StreamContext对象
Args:
context: StreamContext对象包含聊天流的所有消息信息
unread_messages: (可选) 指定要处理的未读消息列表,用于并发处理
Returns:
处理结果字典
@@ -68,10 +69,12 @@ class AffinityChatter(BaseChatter):
learner = expression_learner_manager.get_expression_learner(self.stream_id)
asyncio.create_task(learner.trigger_learning_for_chat())
unread_messages = context.get_unread_messages()
# 如果没有提供未读消息列表,则从上下文中获取
if unread_messages is None:
unread_messages = context.get_unread_messages()
# 使用增强版规划器处理消息
actions, target_message = await self.planner.plan(context=context)
actions, target_message = await self.planner.plan(context=context, unread_messages=unread_messages)
self.stats["plans_created"] += 1
# 执行动作(如果规划器返回了动作)

View File

@@ -218,10 +218,6 @@ class ChatterPlanFilter:
self.last_obs_time_mark = time.time()
mentioned_bonus = ""
if global_config.chat.mentioned_bot_inevitable_reply:
mentioned_bonus = "\n- 有人提到你"
if global_config.chat.at_bot_inevitable_reply:
mentioned_bonus = "\n- 有人提到你或者at你"
if plan.mode == ChatMode.FOCUS:
no_action_block = """

View File

@@ -70,12 +70,15 @@ class ChatterActionPlanner:
"other_actions_executed": 0,
}
async def plan(self, context: "StreamContext" = None) -> Tuple[List[Dict], Optional[Dict]]:
async def plan(
self, context: "StreamContext" = None, unread_messages: Optional[List[Dict]] = None
) -> Tuple[List[Dict], Optional[Dict]]:
"""
执行完整的增强版规划流程。
Args:
context (StreamContext): 包含聊天流消息的上下文对象。
unread_messages (Optional[List[Dict]]): (可选) 指定要处理的未读消息列表,用于并发处理
Returns:
Tuple[List[Dict], Optional[Dict]]: 一个元组,包含:
@@ -85,14 +88,16 @@ class ChatterActionPlanner:
try:
self.planner_stats["total_plans"] += 1
return await self._enhanced_plan_flow(context)
return await self._enhanced_plan_flow(context, unread_messages)
except Exception as e:
logger.error(f"规划流程出错: {e}")
self.planner_stats["failed_plans"] += 1
return [], None
async def _enhanced_plan_flow(self, context: "StreamContext") -> Tuple[List[Dict], Optional[Dict]]:
async def _enhanced_plan_flow(
self, context: "StreamContext", unread_messages: Optional[List[Dict]] = None
) -> Tuple[List[Dict], Optional[Dict]]:
"""执行增强版规划流程"""
try:
# 在规划前,先进行动作修改
@@ -106,7 +111,10 @@ class ChatterActionPlanner:
# 确保Plan中包含所有当前可用的动作
initial_plan.available_actions = self.action_manager.get_using_actions()
unread_messages = context.get_unread_messages() if context else []
# 如果没有提供未读消息列表,则从上下文中获取
if unread_messages is None:
unread_messages = context.get_unread_messages() if context else []
# 2. 兴趣度评分 - 只对未读消息进行评分
if unread_messages:
bot_nickname = global_config.bot.nickname