From dceb9061e83ccfb7b3dd0827856e9521d627b6f1 Mon Sep 17 00:00:00 2001 From: root <953994191@qq.com> Date: Wed, 6 May 2026 14:45:40 +0800 Subject: [PATCH] =?UTF-8?q?=E9=87=8D=E6=9E=84=EF=BC=9A=E7=A7=BB=E9=99=A4?= =?UTF-8?q?=E5=AF=B9=20debug=5Finfo=20=E7=9A=84=E4=BE=9D=E8=B5=96=EF=BC=8C?= =?UTF-8?q?=E5=8F=AA=E4=BD=BF=E7=94=A8=E6=96=B0=E7=9A=84=E7=BB=93=E6=9E=84?= =?UTF-8?q?=E5=8C=96=E7=8A=B6=E6=80=81=E5=AD=97=E6=AE=B5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- backend/app/main_graph/nodes/fast_paths.py | 29 +++++++++++-------- backend/app/main_graph/nodes/hybrid_router.py | 20 ++++--------- backend/app/main_graph/nodes/rag_nodes.py | 26 ++++------------- backend/app/main_graph/nodes/reasoning.py | 12 ++------ 4 files changed, 30 insertions(+), 57 deletions(-) diff --git a/backend/app/main_graph/nodes/fast_paths.py b/backend/app/main_graph/nodes/fast_paths.py index ece7103..b076937 100644 --- a/backend/app/main_graph/nodes/fast_paths.py +++ b/backend/app/main_graph/nodes/fast_paths.py @@ -44,9 +44,6 @@ async def fast_chitchat_node(state: MainGraphState, config: Optional[RunnableCon # 标记快速路径成功,但不设置 final_result,让 llm_call 生成回答 state.success = True state.current_phase = "llm_call" - state.debug_info["fast_chitchat_success"] = True - - # 更新新的结构化字段 state.fast_path.chitchat_success = True # 发送完成事件 @@ -168,7 +165,7 @@ async def _generate_fast_answer(state: MainGraphState, query: str) -> MainGraphS state.final_result = full_content state.success = True state.current_phase = "finalizing" - state.debug_info["fast_rag_success"] = True + state.fast_path.rag_success = True return state except Exception as e: @@ -181,8 +178,8 @@ async def fast_tool_node(state: MainGraphState, config: Optional[RunnableConfig] """快速工具节点""" state.current_phase = "fast_tool" - decision = state.debug_info.get("hybrid_decision", {}) - suggested_tools = decision.get("suggested_tools", []) + decision = state.hybrid_router.decision + suggested_tools = decision.suggested_tools if (decision and hasattr(decision, 'suggested_tools')) else [] info(f"[Fast Tool] 开始处理,建议工具: {suggested_tools}") await dispatch_custom_event("fast_path_start", {"path": "fast_tool", "suggested_tools": suggested_tools}, config) @@ -197,16 +194,23 @@ async def fast_tool_node(state: MainGraphState, config: Optional[RunnableConfig] return _mark_fast_path_failed(state, "快速工具调用暂未完善") +# ========== 条件路由函数 ========== +def check_fast_path_success(state: MainGraphState) -> str: + """检查快速路径是否成功 - 使用新的结构化字段""" + if state.fast_path.failed: + info("[Fast Path Check] 快速路径失败,升级到 React 循环") + return "escalate" + + info("[Fast Path Check] 快速路径成功,进入 llm_call") + return "llm_call" + + # ========== 公共函数 ========== def _mark_fast_path_failed(state: MainGraphState, reason: str = "") -> MainGraphState: - """标记快速路径失败,准备升级到 React 循环""" - state.debug_info["fast_path_failed"] = True - state.debug_info["fast_path_fail_reason"] = reason - state.success = False - - # 更新新的结构化字段 + """标记快速路径失败,准备升级到 React 循环 - 使用新的结构化字段""" state.fast_path.failed = True state.fast_path.fail_reason = reason + state.success = False info(f"[Fast Path] 标记失败,准备升级: {reason}") return state @@ -217,5 +221,6 @@ __all__ = [ "fast_chitchat_node", "fast_rag_node", "fast_tool_node", + "check_fast_path_success", "_mark_fast_path_failed", ] diff --git a/backend/app/main_graph/nodes/hybrid_router.py b/backend/app/main_graph/nodes/hybrid_router.py index ad5dd2b..072782a 100644 --- a/backend/app/main_graph/nodes/hybrid_router.py +++ b/backend/app/main_graph/nodes/hybrid_router.py @@ -187,17 +187,7 @@ async def hybrid_router_node(state: MainGraphState, config: Optional[RunnableCon info("[Hybrid Router] 规则未命中,使用 LLM 分类") decision = await _classify_with_llm(query) - # 3. 更新状态(同时更新旧的 debug_info 和新的结构化字段) - state.debug_info["hybrid_decision"] = { - "intent": decision.intent, - "confidence": decision.confidence, - "path": decision.path, - "reasoning": decision.reasoning, - "suggested_tools": decision.suggested_tools - } - state.debug_info["hybrid_start_time"] = datetime.now().isoformat() - - # 更新新的结构化字段 + # 步骤3: 更新状态 - 只使用新的结构化字段 state.hybrid_router.decision = decision state.hybrid_router.start_time = datetime.now().isoformat() @@ -221,9 +211,11 @@ async def hybrid_router_node(state: MainGraphState, config: Optional[RunnableCon # ========== 条件路由函数 ========== def route_from_hybrid_decision(state: MainGraphState) -> str: - """从混合路由决策获取下一步节点""" - decision = state.debug_info.get("hybrid_decision", {}) - return decision.get("path", "react_loop") + """从混合路由决策获取下一步节点 - 使用新的结构化字段""" + decision = state.hybrid_router.decision + if decision and hasattr(decision, 'path'): + return decision.path + return "react_loop" def check_fast_path_success(state: MainGraphState) -> str: diff --git a/backend/app/main_graph/nodes/rag_nodes.py b/backend/app/main_graph/nodes/rag_nodes.py index f66a1ad..87893fe 100644 --- a/backend/app/main_graph/nodes/rag_nodes.py +++ b/backend/app/main_graph/nodes/rag_nodes.py @@ -48,8 +48,8 @@ async def _rag_retrieve_core(state: MainGraphState, pipeline) -> MainGraphState: """执行 RAG 检索的核心逻辑""" retrieval_query = state.user_query - # 优先使用推理结果中的优化查询 - reasoning_result = state.debug_info.get("reasoning_result") + # 优先使用推理结果中的优化查询 - 从新的结构化字段获取 + reasoning_result = state.react_reasoning.reasoning_result if reasoning_result and hasattr(reasoning_result, "retrieval_config"): cfg = reasoning_result.retrieval_config if cfg and cfg.retrieval_query: @@ -67,8 +67,7 @@ async def _rag_retrieve_core(state: MainGraphState, pipeline) -> MainGraphState: state.rag_docs = documents # 保存文档用于置信度评估 state.rag_retrieved = bool(documents) # 有文档才算检索成功 state.rag_attempts = getattr(state, 'rag_attempts', 0) + 1 - state.debug_info["rag_source"] = "pipeline" - state.debug_info["rag_scores"] = pipeline.last_scores # 保存分数信息 + # 移除对 debug_info 的依赖,不再保存 rag_scores return state @@ -148,16 +147,7 @@ async def _evaluate_rag_confidence(state: MainGraphState) -> float: def _get_embedding_similarity(state: MainGraphState) -> float: - """从 rag_scores 或 rag_docs 中获取向量相似度分数""" - # 优先从 pipeline 提供的分数中获取 - rag_scores = state.debug_info.get("rag_scores", []) - if rag_scores: - scores = [s.get("embedding_score", 0.0) for s in rag_scores] - if scores: - # 归一化到 0-1 - normalized = [min(s / 10.0, 1.0) if s > 1.0 else s for s in scores] - return max(normalized) - + """从 rag_docs 中获取向量相似度分数(不再从 debug_info 获取)""" # 降级:从 rag_docs 中获取 rag_docs = getattr(state, "rag_docs", []) scores = [] @@ -176,13 +166,7 @@ def _get_embedding_similarity(state: MainGraphState) -> float: def _get_rerank_score(state: MainGraphState) -> float: - """从 rag_scores 或 rag_docs 中获取重排序分数""" - # 优先从 pipeline 提供的分数中获取 - rag_scores = state.debug_info.get("rag_scores", []) - if rag_scores: - scores = [s.get("rerank_score", 0.0) for s in rag_scores] - return max(scores) if scores else 0.0 - + """从 rag_docs 中获取重排序分数(不再从 debug_info 获取)""" # 降级:从 rag_docs 中获取 rag_docs = getattr(state, "rag_docs", []) scores = [] diff --git a/backend/app/main_graph/nodes/reasoning.py b/backend/app/main_graph/nodes/reasoning.py index faa2bd0..92ed312 100644 --- a/backend/app/main_graph/nodes/reasoning.py +++ b/backend/app/main_graph/nodes/reasoning.py @@ -47,22 +47,14 @@ async def react_reason_node(state: MainGraphState, config: Optional[RunnableConf "timestamp": datetime.now().isoformat() }) - # 步骤4: 更新调试信息(同时更新旧的 debug_info 和新的结构化字段) - state.debug_info["last_reasoning"] = { - "action": result.action.name, - "confidence": result.confidence, - "reasoning": result.reasoning - } - state.debug_info["reasoning_result"] = result - state.last_action = result.action.name - - # 更新新的结构化字段 + # 步骤3: 更新状态 - 只使用新的结构化字段 state.react_reasoning.last_reasoning = { "action": result.action.name, "confidence": result.confidence, "reasoning": result.reasoning } state.react_reasoning.reasoning_result = result + state.last_action = result.action.name # 步骤5: 发送推理事件 await dispatch_custom_event(