From e6a1643bea2acae5f66f1e4c2c0abbb405faff35 Mon Sep 17 00:00:00 2001 From: Mark Date: Wed, 7 Jan 2026 19:35:29 +0800 Subject: [PATCH] [modfiy] default_model_config_id miss error --- api/app/services/app_service.py | 37 +++--- api/app/services/handoffs_service.py | 130 ++++++++++--------- api/app/services/multi_agent_orchestrator.py | 85 ++++++------ 3 files changed, 124 insertions(+), 128 deletions(-) diff --git a/api/app/services/app_service.py b/api/app/services/app_service.py index 046bb9a2..7a4e46fb 100644 --- a/api/app/services/app_service.py +++ b/api/app/services/app_service.py @@ -203,27 +203,28 @@ class AppService: "多智能体配置未激活,无法运行", BizCode.AGENT_CONFIG_MISSING ) - if not multi_agent_config.default_model_config_id: - # # 2. 检查主 Agent 配置 - if not multi_agent_config.master_agent_id: - raise BusinessException( - "未配置主 Agent,无法运行", - BizCode.AGENT_CONFIG_MISSING - ) + if multi_agent_config.orchestration_mode == "supervisor": + if not multi_agent_config.default_model_config_id: + # # 2. 检查主 Agent 配置 + if not multi_agent_config.master_agent_id: + raise BusinessException( + "未配置主 Agent,无法运行", + BizCode.AGENT_CONFIG_MISSING + ) - master_agent_release = self.db.get(AppRelease, multi_agent_config.master_agent_id) - if not master_agent_release: - raise BusinessException( - f"主 Agent 配置不存在: {multi_agent_config.master_agent_id}", - BizCode.AGENT_CONFIG_MISSING - ) + master_agent_release = self.db.get(AppRelease, multi_agent_config.master_agent_id) + if not master_agent_release: + raise BusinessException( + f"主 Agent 配置不存在: {multi_agent_config.master_agent_id}", + BizCode.AGENT_CONFIG_MISSING + ) - # 检查主 Agent 的模型配置 - multi_agent_config.default_model_config_id = master_agent_release.default_model_config_id + # 检查主 Agent 的模型配置 + multi_agent_config.default_model_config_id = master_agent_release.default_model_config_id - model_api_key = ModelApiKeyService.get_a_api_key(self.db, multi_agent_config.default_model_config_id) - if not model_api_key: - raise ResourceNotFoundException("模型配置", str(multi_agent_config.default_model_config_id)) + model_api_key = ModelApiKeyService.get_a_api_key(self.db, multi_agent_config.default_model_config_id) + if not model_api_key: + raise ResourceNotFoundException("模型配置", str(multi_agent_config.default_model_config_id)) # 3. 检查子 Agent 配置 diff --git a/api/app/services/handoffs_service.py b/api/app/services/handoffs_service.py index 45232339..be32b864 100644 --- a/api/app/services/handoffs_service.py +++ b/api/app/services/handoffs_service.py @@ -253,7 +253,7 @@ def route_after_agent(state: HandoffState) -> str: def convert_multi_agent_config_to_handoffs( multi_agent_config: Dict, db: Session -) -> tuple[Dict[str, Dict], RedBearModelConfig]: +) -> Dict[str, Dict]: """将 multi_agent_config 转换为 handoffs 配置格式 Args: @@ -261,7 +261,7 @@ def convert_multi_agent_config_to_handoffs( db: 数据库会话 Returns: - (agent_configs, model_config) 元组 + agent_configs 字典,每个 Agent 包含自己的 model_config """ from app.models import AppRelease, App @@ -271,45 +271,77 @@ def convert_multi_agent_config_to_handoffs( # 遍历子 Agent,构建配置 for sub_agent in sub_agents: - agent_app_id = sub_agent.get("agent_id") - agent_name = sub_agent.get("name", f"agent_{agent_app_id[:8] if agent_app_id else 'unknown'}") + agent_id = sub_agent.get("agent_id") # 可能是 release_id 或 app_id + agent_name = sub_agent.get("name", f"agent_{agent_id[:8] if agent_id else 'unknown'}") # 使用安全的 agent name(去除特殊字符) safe_name = agent_name.replace(" ", "_").replace("-", "_").lower() agent_names.append(safe_name) - # 从 AppRelease 获取 Agent 的系统提示词 + # 从 AppRelease 获取 Agent 的系统提示词和模型配置 system_prompt = f"你是 {agent_name}。" capabilities = sub_agent.get("capabilities", []) + model_config = None + release = None - if agent_app_id: + if agent_id: try: - agent_app_id_uuid = uuid.UUID(agent_app_id) if isinstance(agent_app_id, str) else agent_app_id - # 获取应用的当前发布版本 - app = db.get(App, agent_app_id_uuid) - if app and app.current_release_id: - release = db.get(AppRelease, app.current_release_id) - if release and release.config: + agent_id_uuid = uuid.UUID(agent_id) if isinstance(agent_id, str) else agent_id + + # 先尝试作为 release_id 查询 + release = db.get(AppRelease, agent_id_uuid) + + # 如果找不到,尝试作为 app_id 查询,获取 current_release + if not release: + app = db.get(App, agent_id_uuid) + if app and app.current_release_id: + release = db.get(AppRelease, app.current_release_id) + + if release: + # 从 release.config 获取 system_prompt + if release.config: config_data = release.config - # 从 release.config 获取 system_prompt release_system_prompt = config_data.get("system_prompt") if release_system_prompt: system_prompt = release_system_prompt - logger.debug(f"从 AppRelease 获取 Agent {agent_name} 的系统提示词") + + # 获取该 Agent 的模型配置 + if release.default_model_config_id: + model_api_key = ModelApiKeyService.get_a_api_key(db, release.default_model_config_id) + if model_api_key: + model_config = RedBearModelConfig( + model_name=model_api_key.model_name, + provider=model_api_key.provider, + api_key=model_api_key.api_key, + base_url=model_api_key.api_base, + extra_params={ + "temperature": 0.7, + "max_tokens": 2000, + "streaming": True + } + ) + logger.debug(f"Agent {agent_name} 使用模型: {model_api_key.model_name}") + else: + logger.warning(f"Agent {agent_name} 模型配置无效: {release.default_model_config_id}") + else: + logger.warning(f"Agent {agent_name} 没有配置 default_model_config_id") + else: + logger.warning(f"Agent {agent_name} 找不到发布版本: agent_id={agent_id}") except Exception as e: - logger.warning(f"获取 Agent {agent_name} 的系统提示词失败: {str(e)}") + logger.warning(f"获取 Agent {agent_name} 配置失败: {str(e)}") # 如果有 capabilities,添加到系统提示词 - if capabilities and not system_prompt.endswith("。"): - system_prompt += f" 你的专长是: {', '.join(capabilities)}。" - elif capabilities: + if capabilities: + if not system_prompt.endswith("。"): + system_prompt += "。" system_prompt += f" 你的专长是: {', '.join(capabilities)}。" agent_configs[safe_name] = { - "agent_id": agent_app_id, + "agent_id": agent_id, "name": agent_name, "description": f"转移到 {agent_name}。{sub_agent.get('role') or ''}", "system_prompt": system_prompt, "capabilities": capabilities, + "model_config": model_config, # 每个 Agent 自己的模型配置 "can_transfer_to": [] # 稍后填充 } @@ -327,38 +359,7 @@ def convert_multi_agent_config_to_handoffs( transfer_instructions += f"\n- transfer_to_{other_name}: {other_config['description']}" agent_configs[safe_name]["system_prompt"] += transfer_instructions - # 获取 LLM 配置 - model_config = None - default_model_config_id = multi_agent_config.get("default_model_config_id") - if default_model_config_id: - model_api_key = ModelApiKeyService.get_a_api_key(db, default_model_config_id) - if model_api_key: - # 获取模型参数 - model_parameters = multi_agent_config.get("model_parameters") - temperature = 0.7 - max_tokens = 2000 - - if model_parameters: - if hasattr(model_parameters, 'temperature'): - temperature = model_parameters.temperature - max_tokens = model_parameters.max_tokens or 2000 - elif isinstance(model_parameters, dict): - temperature = model_parameters.get("temperature", 0.7) - max_tokens = model_parameters.get("max_tokens", 2000) - - model_config = RedBearModelConfig( - model_name=model_api_key.model_name, - provider=model_api_key.provider, - api_key=model_api_key.api_key, - base_url=model_api_key.api_base, - extra_params={ - "temperature": temperature, - "max_tokens": max_tokens, - "streaming": True - } - ) - - return agent_configs, model_config + return agent_configs # ==================== Handoffs 服务类 ==================== @@ -369,21 +370,23 @@ class HandoffsService: def __init__( self, agent_configs: Dict[str, Dict], - model_config: RedBearModelConfig, streaming: bool = True ): """初始化 Handoffs 服务 Args: - agent_configs: Agent 配置字典 - model_config: RedBearModelConfig 模型配置 + agent_configs: Agent 配置字典,每个 Agent 包含自己的 model_config streaming: 是否启用流式输出 """ self.agent_configs = agent_configs - self.model_config = model_config self.streaming = streaming self._graph = None + # 验证每个 Agent 都有模型配置 + for agent_name, config in agent_configs.items(): + if not config.get("model_config"): + raise ValueError(f"Agent {agent_name} 没有配置模型") + logger.info(f"HandoffsService 初始化, agents: {list(self.agent_configs.keys())}") def _build_graph(self): @@ -392,25 +395,29 @@ class HandoffsService: agent_names = list(self.agent_configs.keys()) if not agent_names: + raise ValueError("至少需要一个 Agent 配置") for agent_name in agent_names: config = self.agent_configs[agent_name] tools = create_tools_for_agent(agent_name, self.agent_configs) + # 使用每个 Agent 自己的模型配置 + agent_model_config = config.get("model_config") + if self.streaming: agent_node = create_streaming_agent_node( agent_name=agent_name, system_prompt=config.get("system_prompt", f"你是 {agent_name}"), tools=tools, - model_config=self.model_config + model_config=agent_model_config ) else: agent_node = create_agent_node( agent_name=agent_name, system_prompt=config.get("system_prompt", f"你是 {agent_name}"), tools=tools, - model_config=self.model_config + model_config=agent_model_config ) builder.add_node(agent_name, agent_node) @@ -569,17 +576,14 @@ def get_handoffs_service_for_app( if not multi_agent_config: raise ValueError(f"应用 {app_id} 没有多 Agent 配置") - # 转换配置 - agent_configs, model_config = convert_multi_agent_config_to_handoffs(multi_agent_config, db) + # 转换配置(每个 Agent 包含自己的 model_config) + agent_configs = convert_multi_agent_config_to_handoffs(multi_agent_config, db) if not agent_configs: raise ValueError(f"应用 {app_id} 没有配置子 Agent") - if not model_config: - raise ValueError(f"应用 {app_id} 没有配置模型") - # 创建服务 - service = HandoffsService(agent_configs, model_config, streaming) + service = HandoffsService(agent_configs, streaming) # 缓存 _service_cache[cache_key] = service diff --git a/api/app/services/multi_agent_orchestrator.py b/api/app/services/multi_agent_orchestrator.py index 1369e2f4..bb788641 100644 --- a/api/app/services/multi_agent_orchestrator.py +++ b/api/app/services/multi_agent_orchestrator.py @@ -54,29 +54,34 @@ class MultiAgentOrchestrator: # 初始化会话状态管理器 self.state_manager = ConversationStateManager() - # 获取 Master Agent 的模型配置 - if not self.default_model_config_id: - raise BusinessException("Master Agent 缺少模型配置", BizCode.AGENT_CONFIG_MISSING) + # 只有 supervisor 模式才需要 default_model_config_id 和 router + self.master_model_config = None + self.router = None + + if self._normalized_mode == OrchestrationMode.SUPERVISOR: + # 获取 Master Agent 的模型配置 + if not self.default_model_config_id: + raise BusinessException("Supervisor 模式需要配置默认模型", BizCode.AGENT_CONFIG_MISSING) - self.master_model_config = self.db.get(ModelConfig, self.default_model_config_id) - if not self.master_model_config: - raise BusinessException("Master Agent 模型配置不存在", BizCode.AGENT_CONFIG_MISSING) + self.master_model_config = self.db.get(ModelConfig, self.default_model_config_id) + if not self.master_model_config: + raise BusinessException("Master Agent 模型配置不存在", BizCode.AGENT_CONFIG_MISSING) - # 初始化 Master Agent 路由器 - self.router = MasterAgentRouter( - db=db, - master_model_config=self.master_model_config, - model_parameters=self.model_parameters, - sub_agents=self.sub_agents, - state_manager=self.state_manager, - enable_rule_fast_path=config.execution_config.get("enable_rule_fast_path", True) - ) + # 初始化 Master Agent 路由器 + self.router = MasterAgentRouter( + db=db, + master_model_config=self.master_model_config, + model_parameters=self.model_parameters, + sub_agents=self.sub_agents, + state_manager=self.state_manager, + enable_rule_fast_path=config.execution_config.get("enable_rule_fast_path", True) + ) logger.info( "多 Agent 编排器初始化完成", extra={ "config_id": str(config.id), - "model": self.master_model_config.name, + "model": self.master_model_config.name if self.master_model_config else None, "sub_agent_count": len(self.sub_agents), "orchestration_mode": self._normalized_mode } @@ -139,15 +144,11 @@ class MultiAgentOrchestrator: "timestamp": time.time() }) - # 1. 主 Agent 分析任务 - task_analysis = await self._analyze_task(message, variables) - task_analysis["use_llm_routing"] = use_llm_routing - # 2. 根据模式执行(流式) - # Supervisor 模式:由主 Agent 统一调度子 Agent - if self._normalized_mode == OrchestrationMode.SUPERVISOR: - async for event in self._execute_conditional_stream( - task_analysis, + # Collaboration 模式:Agent 之间可以相互 handoff(使用 handoffs_service) + if self._normalized_mode == OrchestrationMode.COLLABORATION: + async for event in self._execute_collaboration_mode_stream( + message, conversation_id, user_id, web_search, @@ -156,9 +157,13 @@ class MultiAgentOrchestrator: user_rag_memory_id ): yield event - # Collaboration 模式:Agent 之间可以相互 handoff(使用 handoffs_service) - elif self._normalized_mode == OrchestrationMode.COLLABORATION: - async for event in self._execute_collaboration_mode_stream( + # Supervisor 模式:由主 Agent 统一调度子 Agent + elif self._normalized_mode == OrchestrationMode.SUPERVISOR: + # 1. 主 Agent 分析任务 + task_analysis = await self._analyze_task(message, variables) + task_analysis["use_llm_routing"] = use_llm_routing + + async for event in self._execute_conditional_stream( task_analysis, conversation_id, user_id, @@ -1406,7 +1411,7 @@ class MultiAgentOrchestrator: async def _execute_collaboration_mode_stream( self, - task_analysis: Dict[str, Any], + message: str, conversation_id: Optional[uuid.UUID], user_id: Optional[str], web_search: bool = False, @@ -1419,7 +1424,7 @@ class MultiAgentOrchestrator: 使用 handoffs_service 实现 Agent 之间的动态切换 Args: - task_analysis: 任务分析结果 + message: 用户消息 conversation_id: 会话 ID user_id: 用户 ID web_search: 是否启用网络搜索 @@ -1435,19 +1440,15 @@ class MultiAgentOrchestrator: HandoffsService ) - message = task_analysis.get("message", "") - try: # 1. 构建 multi_agent_config 字典 multi_agent_config = { "sub_agents": self.config.sub_agents, - "default_model_config_id": self.config.default_model_config_id, - "model_parameters": self.config.model_parameters, "orchestration_mode": self.config.orchestration_mode } - # 2. 转换配置 - agent_configs, model_config = convert_multi_agent_config_to_handoffs( + # 2. 转换配置(每个 Agent 包含自己的 model_config) + agent_configs = convert_multi_agent_config_to_handoffs( multi_agent_config, self.db ) @@ -1455,13 +1456,9 @@ class MultiAgentOrchestrator: if not agent_configs: raise BusinessException("没有可用的子 Agent", BizCode.AGENT_CONFIG_MISSING) - if not model_config: - raise BusinessException("没有配置模型", BizCode.AGENT_CONFIG_MISSING) - # 3. 创建 HandoffsService handoffs_service = HandoffsService( agent_configs=agent_configs, - model_config=model_config, streaming=True ) @@ -1513,13 +1510,11 @@ class MultiAgentOrchestrator: # 1. 构建 multi_agent_config 字典 multi_agent_config = { "sub_agents": self.config.sub_agents, - "default_model_config_id": self.config.default_model_config_id, - "model_parameters": self.config.model_parameters, "orchestration_mode": self.config.orchestration_mode } - # 2. 转换配置 - agent_configs, model_config = convert_multi_agent_config_to_handoffs( + # 2. 转换配置(每个 Agent 包含自己的 model_config) + agent_configs = convert_multi_agent_config_to_handoffs( multi_agent_config, self.db ) @@ -1527,13 +1522,9 @@ class MultiAgentOrchestrator: if not agent_configs: raise BusinessException("没有可用的子 Agent", BizCode.AGENT_CONFIG_MISSING) - if not model_config: - raise BusinessException("没有配置模型", BizCode.AGENT_CONFIG_MISSING) - # 3. 创建 HandoffsService handoffs_service = HandoffsService( agent_configs=agent_configs, - model_config=model_config, streaming=False )