ARTICLE DETAIL

资讯详情

深耕网站视觉设计与运营推广的一线实战洞察。

Agno 环境评估入门:用 K-attempt 通过率网格量化 Agent 可靠性

Agno 环境评估入门:用 K-attempt 通过率网格量化 Agent 可靠性 Agno 环境评估入门用 K-attempt 通过率网格量化 Agent 可靠性【免费下载链接】agnoBuild, run, and manage agent platforms.项目地址: https://gitcode.com/GitHub_Trending/ag/agno本篇技术指南围绕 Agno 仓库中cookbook/environments/_01_first_environment目录展开讲解如何用 Environment run_rollouts 让同一个 Agent 对一组任务反复运行 K 次并逐次评分把偶然一次跑通升级为可量化的通过率网格。读完本文你将掌握三个可直接运行的实战脚本basic.py、with_summary.py、with_fingerprints.py的完整写法理解学习区learning zone的判定逻辑并学会用环境指纹与策略指纹审计一次评估结果的可复现性。为什么需要 Environment单次成功不是证据一次 Agent 运行的成功可能只是运气。Agno 的 Environment 框架提供了一条朴素的可靠性路径让同一个 Agent 对同一组任务运行 K 次、每次单独评分最终输出一张通过率网格。网格的价值在于把结果分成三类对应三种不同的处置手段全满的行4/4、8/8任务已被掌握无需额外干预全空的行0/4需要换一种干预思路当前策略对该任务完全不适用部分通过的行如 2/4、3/4位于学习区learning zone既有成功也有失败每一次失败都有一次成功对照是进一步诊断和迭代的核心对象。正如 README.md 所述full rows are already mastered, empty rows need a different intervention, and partial rows are the learning zone全满行表示已掌握空行需要换一种干预部分行才是学习区。该目录定位为整个 environments 系列的第一步在 README 中明确给出适用场景Start here when one successful agent run is not enough evidence当一次成功的 Agent 运行不足以作为证据时从这里开始。最小完整环境basic.py 逐行拆解basic.py被 README 称为the smallest complete environment——一个最小但完整的评估环境由四个要素组成类型化输出typed output、任务集tasks、评分器CodeScorer和 K-attempt 网格。下面是它的完整骨架from agno.agent import Agent from agno.environments import Environment, Task, run_rollouts from agno.models.openai import OpenAIResponses from agno.scorer import CodeScorer from pydantic import BaseModel # 1) 类型化输出声明 Agent 必须以结构化字段返回结果 class Answer(BaseModel): value: int # 2) 评分函数从 run 的结构化内容中取 value 与期望值比较 def answer_matches(run, expected): return run.content.value expected # 3) AgentOpenAIResponses gpt-5.5低推理强度结构化输出 agent Agent( modelOpenAIResponses(idgpt-5.5, reasoning_effortlow), output_schemaAnswer, instructionsReturn only the requested final integer in the typed field., ) # 4) 环境任务集 评分器绑定在一起 environment Environment( namefirst-environment, agentagent, tasks( Task(inputWhat is 17 multiplied by 23?, expected391, ideasy-product), Task(input..., expected20944939, idchained-product-a), Task(input..., expected16731173, idchained-product-b), ), scorerCodeScorer(answer_matches), ) if __name__ __main__: results run_rollouts(environment, k4) print(results)完整可运行版本见 basic.py。几个关键点Task的核心字段input必填的提示文本、expected期望值可为 None、id显示与选择用缺省时按位置自动命名为 t1..tN、metadata可选的附加元数据字典。从源码看Task 是一个frozenTrue, eqFalse的 dataclasseqFalse保证身份语义避免metadata为 dict 时自动生成的__hash__抛错。Environment的约束agent参数只接受Agent实例或零参数的 Agent 工厂函数传入Team会直接抛TypeError见 environment.pytimeout_seconds默认 120 秒。评分器CodeScorer接受任何(run, expected) - bool | float | Score形式的可调用对象。bool直接映射为 1.0/0.0 且不经过阈值判断float会与pass_threshold默认 0.5比较Score原样使用。由于output_schema存在时run.content是 pydantic 模型而非字符串直接用run.content.value expected比较类型化字段是官方推荐写法见 code.py。任务集设计易锚点 校准链式乘积basic.py的任务集并非随机拼凑而是刻意设计的两层结构easy-product易锚点两位数乘法17 × 23 391用于确认 Agent 与评分链路本身工作正常几乎必然全过chained-product-a/b校准链式乘积提示中包含计算两个 16 位大数乘积 → 求其十进制数位之和 → 乘以一个大质数 → 减去乘积对另一个质数取模的余数 → 返回最终整数这样的多步运算。这类任务特意被校准为在gpt-5.5上产生通过/失败分歧。这种易锚点 会分歧的难任务的组合是有意为之README 明确警告an all-full grid is not a useful reliability example全满的网格不是有用的可靠性示例。如果每个任务都 4/4 全过你无法区分Agent 真的强和任务太简单测不出东西必须保留若干落在部分通过区间的行网格才有诊断价值。用 summary() 读取网格脚本与 CI 的稳定契约with_summary.py演示了如何把同一张网格读成稳定的字典结构供脚本与 CI 使用。核心调用与输出results run_rollouts(environment, k4) print(results) summary results.summary() print(foverall pass rate: {summary[pass_rate]}) print(fscored attempts: {summary[n_scored]} of {summary[n_attempts]}) for task in summary[tasks]: print( f{task[id]}: pass_rate{task[pass_rate]}, funscored{task[n_unscored]}, learning_zone{task[learning_zone]} )从 runner.py 中的 summary() 实现 可以看到该返回字典的完整键集这些键是冻结的 CI 契约键含义env/k环境名与尝试次数n_tasks/n_attempts/n_scored/n_unscored任务数、总尝试数、成功计分尝试数、未计分尝试数pass_rate/mean_value总体通过率与得分均值未计分尝试被排除统计绝不强行按 0 分处理——超时不是答错env_fingerprint/policy_fingerprint环境指纹与策略指纹见下节stopped_early提前终止原因如error-storm或 Nonetasks每行任务的id、pass_rate、mean_value、n_unscored、learning_zone其中learning_zone的判定实现位于TaskResult.in_learning_zonerunner.py当且仅当0 n_passed n_scored即部分计分尝试通过、部分失败。这与 TEST_LOG 中描述的 Agno 2.8.0 学习区定义0 pass_rate 1混合通过/失败完全一致。注意一个细节with_summary.py中的锚点任务是 29 × 31且chained-product-b用的是另一组校准参数modulo 32749期望 10481347与basic.py不同——这是刻意让每个示例独立校准避免不同脚本共享同一校准链导致的结果纠缠。指纹审计环境指纹与策略指纹with_fingerprints.py展示了结果对象上保留的两枚指纹。运行时输出results run_rollouts(environment, k4) print(results) summary results.summary() print(fenvironment fingerprint: {summary[env_fingerprint]}) print(fpolicy fingerprint: {summary[policy_fingerprint]}) print(fenvironment matches result: {environment.env_matches(results)})两枚指纹的分工见 environment.py 的 docstring 与实现环境指纹env_fingerprint对任务的(id, input, expected)三元组、评分器摘要、声明的工具 schema、tool_choice、所有塑造提示的字符串instructions、description、system_message、additional_context、expected_output、role、additional_input、提示相关开关markdown、是否注入名字/位置/日期时间/会话状态以及终止设置timeout_seconds、tool_call_limit做规范化 JSON 后的 sha256。它带版本前缀envfp2版本不同的指纹永远不相等。改动评分器、任务或提示文本都会改变环境指纹。策略指纹policy_fingerprint对模型身份做 sha256——模型类、id、provider、base_url 以及所有枚举的请求参数。换模型如 gpt-5.5 换成 gpt-5.5-mini会改变策略指纹。env_matches()在任意一侧指纹为 None 时返回 False防止两边都是 None 时用 误判为匹配的假绿见 environment.py。运行时指纹会在 run 开始时计算并盖印在结果上若某个组件无法指纹化会降级为 None 并给出警告而不是让整个 run 崩溃。另有两个值得注意的工程细节指纹对 message 的id与created_at这两个每次构造都会变化的易变字段做了剥离见_VOLATILE_MESSAGE_KEYS而add_datetime_to_context这类注入墙钟时间的开关则按开关值而非渲染文本参与哈希从而保证指纹跨运行可复现。运行方式与依赖三个脚本的运行方式完全一致python cookbook/environments/_01_first_environment/basic.py python cookbook/environments/_01_first_environment/with_summary.py python cookbook/environments/_01_first_environment/with_fingerprints.py运行前提需要设置OPENAI_API_KEY。每次模型调用都通过OpenAIResponses使用gpt-5.5。脚本在if __name__ __main__:保护下执行run_rollouts(environment, k4)——k4 意味着每个任务跑 4 次三个任务共 12 次尝试。从 arun_rollouts 的签名 看run_rollouts的默认参数为k8、concurrency4还支持tasks从 env.tasks 中按身份选择子集与model模型覆盖两个可选参数。实测记录解读TEST_LOG 中的真实结果TEST_LOG.md 记录了 2026-07-20 在 Agno 2.7.4 下用gpt-5.5实测并通过PASS的结果以及在 Agno 2.8.0 源码下的重测。这些数字是理解网格语义的最佳注脚basic.py12/12 次尝试全部计分、无未计分尝试。实测通过率easy-product4/41.00、chained-product-a2/40.50、chained-product-b2/40.50。两行链式任务都落在真正的部分通过学习区。with_summary.pyeasy-product4/4、chained-product-a3/40.75、chained-product-c4/4。summary()报告总体通过率 11/12并正确地把chained-product-a标记为唯一的学习区行。with_fingerprints.pyeasy-product4/4、chained-product-a2/40.50、chained-product-b3/40.75结果与环境指纹匹配。TEST_LOG 还记录了一次有代表性的校准迭代with_fingerprints.py首次校准时使用了两个不同的链式任务导致三行全部饱和在 4/4于是替换了任务后才得到上述通过结果。而 2.8.0 重测中发现with_summary.py原校准的chained-product-c与chained-product-a共享边界且在 k4 时会一同饱和于是用一个独立的第二校准链chained-product-b期望 10481347替换之使学习区行在 k4 下稳定可复现。这正体现了网格全满就不是好的可靠性示例这一设计原则在维护中的实际运用校准任务集本身就是一个反复迭代的过程。底层运行原理尝试隔离与网格渲染run_rollouts并不只是简单地循环调用 Agent。从 arun_rollouts 的 docstring 可以提炼出三个决定结果可信度的机制无条件尝试隔离每次尝试都在一个全新的 in-memory 存储与全新 user id 下运行响应缓存关闭运行前会深度复制 Agent或调用工厂构造新实例。这保证尝试之间互不污染、也不会污染你的真实数据——被污染的统计数据会错误地回答我的 Agent 是否可用被污染的轨迹则会毒化训练集。内存、会话摘要、知识/学习写入等副作用路径会被切断但知识读取RAG 检索与学习知识读取仍保留因此带 RAG 的 Agent 在 rollout 中能正常检索。指纹盖印在 run 开始时就计算环境指纹与策略指纹策略指纹基于实际生效的模型计算即使使用了model覆盖也一样并盖印在结果上每次尝试后还会校验采样到的模型 id 与指纹化时一致防止 Agent 子类因deep_copy丢失字段而绿了一次与指纹不符的验证。网格渲染K 次尝试就是 K 个字符——实心块█表示通过、浅色块░表示计分失败、三角▲表示未计分超时/错误。该渲染位于 _render.pyTTY 下通过 rich 实时渲染静态下由EnvironmentRunResult.__str__生成。网格头部会附带总尝试数、耗时与若 provider 报告了总成本。结果对象EnvironmentRunResult还提供了errors()按任务分组错误信息、learning_zone()过滤出仅含学习区任务的结果副本、diff()与基线结果对比指纹不一致会抛MismatchError、save()/load()JSON 往返用于编辑后重跑看什么变了、print_report()与print_attempt()逐尝试的证据明细。其中diff()的语义是环境指纹一致但策略指纹变化时标注policy_changed从而区分提示/任务变了与模型变了两类漂移。已知边界与后续路径README 中明确说明了两点边界其一逐轮奖励turn-by-turn reward的实时反馈环不在此版本中这些 Environment 当前负责的是验证与数据集生成其二若任务需要 id、元数据或检入仓库的 JSONL 文件应继续学习_02_task_setsTask.from_jsonl 支持从 JSONL 加载任务仅允许input/expected/id/metadata四个键未知键会指明行号与键名抛出 ValueError。整个 environments 系列从_00_quickstart的环境速览开始经历_01_first_environment的网格基础、_02_task_sets的任务集管理逐步覆盖代码评分、裁判评分、工具调用评分、学习区、难度校准、异步 rollout、任务选择、SFT 导出等更进阶的主题。建议从本文三个脚本起步先跑通 k4 的网格再逐步引入summary()契约与指纹审计形成一套可复现、可比较、可归档的 Agent 可靠性评估流程。【免费下载链接】agnoBuild, run, and manage agent platforms.项目地址: https://gitcode.com/GitHub_Trending/ag/agno创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表