fix(tools): 同源终态失败后不再重发等价请求 - #301
Closed
ruanzhengxin-zhuxing wants to merge 1 commit into
Closed
Conversation
An Alibaba Cloud 4xx rejects the request shape itself, so an identical request fails identically. Transport retry already excludes those statuses, so the repetition observed in the field (three ROS calls returning HTTP 400 for an unrecognized resource type) came from the agent loop re-issuing equivalent tool calls while the error text was mistaken for a diagnosis. Remember terminal failures per (tool name, canonical input) in the executor and refuse an equivalent call locally instead of hitting the cloud again. aliyun_api marks 4xx results as terminal (408/429 excluded, since those are timing dependent and stay repeatable), the public 4xx message now asks to fix the request or switch to a path that does not depend on the rejected input, and the tools prompt convention forbids resending equivalent requests and requires either a path switch or an explicit conclusion.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
背景
证据会话
2916da860b314205badbbda2356834d9(AnalysisIdsarpt-auto-2026072918)中,ROS 的 ListStackEvents / ListStackResources / GetStack 三次调用都返回 HTTP 400(资源类型ALIYUN::Milvus::Instance无法识别)。Agent 把错误文本当成诊断结论,既没有切换查询路径,也反复重发等价请求。传输层重试策略只覆盖
{429, 502, 503, 504},400 从未被重试,所以重复请求来自 Agent 主循环:ToolExecutor没有"等价请求已终态失败"的记忆,云侧 4xx 也没有和可重试错误区分,公共错误文案还在提示 "before retrying"。改动
新增
src/iac_code/tools/failure_recovery.pyterminal_failure_signature(status, code)生成稳定签名(如http_400:ResourceTypeNotFound)mark_terminal_failure/take_terminal_failure:内部元数据标记_iac_code_terminal_failure,仿照既有TOOL_RENDER_METADATA_KEY约定,在 executor 内被摘除,不会泄漏到事件流或前端TerminalFailureLedger:以(tool_name, canonical_input_sha256)为键的有界 LRU 记忆(128 条)tools/tool_executor.py:执行前查账本,命中则直接返回明确错误(提示先定位根因、再换路径或给出结论),不再真正调用工具;执行后消费并记录终态失败标记。等价性复用既有的canonical_input_sha256。tools/cloud/aliyun/aliyun_api.py:非 2xx 时计算终态签名。408/429 依赖时序而非请求形状,被显式排除,保持可重复。tools/cloud/aliyun/public_errors.py:请求被拒绝的 4xx 文案改为"等价请求会再次被拒绝,请修正请求或切换不依赖该输入的 API 路径",其余状态维持原有可重试提示。agent/system_prompt.py:工具约定新增一条——错误文本是症状不是诊断,禁止重发等价请求,先定位根因,再换路径或给出显式结论。6 个 locale 的
messages.po补齐 3 条新 msgid 的实际译文。测试
tests/tools/test_failure_recovery.py(7 例):签名格式、元数据标记/摘除、账本按 (tool, input) 隔离、LRU 淘汰tests/tools/test_tool_executor.py:新增TestTerminalFailureRecovery(5 例)——等价请求被拒且不再调用工具、内部标记不外泄、不同入参仍执行、非终态失败可重复、无invocation_binding时不记账tests/tools/cloud/aliyun/test_public_errors.py、test_aliyun_api.py、tests/agent/test_system_prompt.py同步覆盖新文案与元数据{s:.0}msgfmt 问题在 baseline 即存在;3 个用git stash验证为 pre-existing;其余 10 个由全量跑自身删除仓库 symlink / 改写__release_date__导致,恢复后重跑 401 通过)ruff check、ruff format --check、ty check全部通过