ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

Agent可观测性实战:从Token核算到链路追踪的排障指南

Agent可观测性实战:从Token核算到链路追踪的排障指南

Agent 应用上线容易,上线之后怎么盯住它别跑偏,是另一回事。我最近帮一个团队排查生产事故,现象很典型:Agent 稳定运行一周后突然响应变慢,Token 账单翻了三倍,可 CPU、内存、带宽全都正常,日志里也找不到一条报错。他们唯一的“可观测性”工具就是数据库慢查询,慢查询确实变多了——但真正的问题根本不在数据库,而在 Agent 的规划循环:一个工具返回了异常格式,Agent 没有识别出来,进入无限重试,每次重试都重新调用一次大模型,单个会话烧掉了几十万 Token。这种故障,传统监控三板斧根本抓不到。

这正是 Agent 可观测性要解决的问题。把分布式追踪、链路诊断、Token 成本精细化核算合起来看,本质上是在回答三件事:这一次 Agent 任务到底经历了什么?出问题时根因在哪一环?整个过程烧了多少 Token、花在哪些环节?这篇文章写给正在做 Agent 应用、又觉得“上线了但心里没底”的团队,也写给准备搭 Agent 可观测体系的平台工程师。文章里不会给你一堆天花乱坠的概念,都是我在实际项目里验证过的埋点方案、排障路径和成本核算方法,你可以直接拿去抄作业。

1. 为什么通用监控套件在 Agent 场景下会失灵:从确定性请求到动态决策链

1.1 传统监控三板斧的假设条件,在 Agent 这里全都不成立了

在传统 Web 服务里,一次请求的路径是确定的:网关进来,经过认证服务,调业务 A,业务 A 调数据库,再调业务 B,最后返回。链路上每个节点的耗时、错误率、饱和度都可以预先定义好,所以指标(Metrics)、日志(Logs)、链路(Traces)这三板斧能很好工作。你画一张拓扑图,哪个节点红了,问题就在哪。

Agent 应用把这件事彻底打乱了。一次用户请求进来,Agent 要根据当前上下文自己决定下一步做什么。同一个问题,昨天走三步就完成了,今天可能绕了二十步还回不来。链路是模型动态生成的,不是代码静态定义的。拓扑图没法画,因为边和节点都是运行时才出现的。更麻烦的是,LLM 调用本身有随机性,同一段 prompt 两次调用结果可能不同,这导致你很难通过复现来定位问题——日志里能找到的只是大量相似但不完全相同的调用记录。

还有个被多数团队忽略的点:传统监控衡量系统健康度靠“错误率”和“延迟”,但 Agent 场景下,一个任务即使没有报错,也可能已经跑偏了很久。我见过一个数据抓取 Agent,上游接口返回的 JSON 结构变了,它反复尝试用各种 prompt 去解析,结果虽然“成功”了,但多花了 17 倍 token,耗时从 8 秒涨到 130 秒。从监控面板看,延迟变高了,但没有任何错误,没有人知道发生了什么。你说这是故障吗?用户体验变差、成本失控,当然是故障。但传统监控会说:一切正常。

1.2 一个真实事故:无报错的性能劣化与“Token 黑洞”

我复盘一下那个事故的完整过程,你就能直观感受到 Agent 可观测性和传统监控的差异。这个 Agent 的核心功能是帮运营人员批量整理商品信息:给定一批商品 ID,调用商品接口拿原始数据,再让 LLM 总结成结构化文案。

上线第一周一切正常。每个商品平均 2 次工具调用、1 次 LLM 调用,单商品成本可控。第二周开始,响应时间从平均 10 秒涨到 40 秒,运营同事开始投诉。当时团队能看到的指标:服务端 CPU 20%,内存 40%,全部正常;日志里没有 error;数据库慢查询有几条,但都是后台任务,和用户投诉时间对不上。一天后账单出来,token 费用涨了 3 倍,团队才意识到问题出在 LLM 调用上。

后来我帮他们把 LLM 调用日志单独拉出来按天聚合,发现问题出在第 9 天。那天有一条技能发布,改动了“商品摘要”的 prompt,把“如果商品描述缺字段,返回示例格式”改成了“请尝试从商品图片信息中补齐”。效果是:Agent 开始对一个缺字段的商品反复调用图像理解工具,每次工具返回结果它都觉得不够,继续让 LLM“再想想”。单个商品的 LLM 调用次数从 1 次变成 18 次,工具调用从 2 次变成 35 次。没有报错,只有 token 账单在加速狂奔。

这就是我常说的 Token 黑洞:一切指标正常,只有 token 消耗在无声扩张。没有 token 计量,这个事故只能等账单出来才发现;有了 token 计量和链路追踪,你可以在第一小时就看到单商品成本异常,并顺着 trace 找到是哪个 prompt 改动造成的。

1.3 Agent 可观测性要回答的三个新问题

所以我的结论是:Agent 可观测性不是把原来的监控体系延长一截,而是新增三个必须被观测的对象。

第一,执行轨迹。Agent 在运行时调用哪些工具、每次调用的参数和结果、模型做了哪些决策、有没有重试和循环。这需要分布式追踪,但 Span 的语义要重新设计,不能用“HTTP 调用”这种粗粒度概念。

第二,Token 消耗。Token 是 Agent 世界的 CPU 时间,是唯一能统一衡量“思考代价”的指标。一次请求烧了多少输入 token、多少输出 token、缓存命中多少,这个数据必须被埋点捕获,否则你既没法控制成本,也没法判断一条链路是不是高效。这个观点和“AI 应用成本分析”领域的主流思路是一致的:把 token 消耗当作应用的一等监控指标来看待。

第三,决策质量。Agent 输出了什么内容、有没有偏离目标、工具结果是否被正确理解。这部分很难自动化评估,但至少要把工具调用的返回状态、模型输出的摘要记录下来,便于事后复盘。很多团队上线 Agent 之后不看日志,就是因为他们觉得“反正模型会自己处理”,但模型处理得好不好,恰恰是最需要看的。

2. 给 Agent 做分布式追踪:Span 类型、埋点设计与全链路串联

2.1 Trace 与 Span 在 Agent 语义下的重新定义

分布式追踪的基本概念大家应该都听过:Trace 是一次完整请求的端到端执行轨迹,Span 是轨迹里的独立工作单元,Span 之间通过 parent-child 关系串联。这个框架本身没有问题,问题在于 Span 怎么定义。

在传统后端,一个 Span 通常对应一次 HTTP 请求、一次 RPC 调用、一次数据库查询。在 Agent 场景,如果你也这么埋,得到的就只是一堆零散的 HTTP 调用记录,根本看不出 Agent 的决策过程。我习惯把 Span 定义为“Agent 在这次任务中做的一件有语义的事情”,而不是“一次网络请求”。

举例来说,一次用户请求可能是:Agent 先分析意图(这是一个 llm.call Span),决定要查订单(这是一个 agent.plan Span),于是调用订单接口(这是一个 tool.call Span),拿到结果后又让模型总结(这是第二个 llm.call Span)。这四个 Span 串起来,才叫“一次 Agent 任务”。如果只记录 HTTP 调用,你会看到两次 LLM 调用分散在树里,它们之间是什么关系、为什么会有第二次,完全不可见。

2.2 我常用的五类 Span 与关键属性清单

我做了几个 Agent 项目后,沉淀了一套相对固定的 Span 类型,在团队里用下来效果不错。不一定是最佳实践,但至少能覆盖大部分诊断场景。

Span 类型span.name 示例父子关系关键属性
任务级agent.task根 Spantask_id、session_id、user_id、goal摘要、agent_name
决策级agent.planparent 为 agent.task决策内容摘要、选择工具、推理摘要
模型调用llm.callparent 为 agent.plan 或 agent.taskprovider、model_name、prompt_tokens、completion_tokens、cache_read_tokens、temperature、max_tokens
工具调用tool.callparent 为 agent.plantool_name、tool_args摘要、tool_result_status、error_type
检索调用retrieval.callparent 为 agent.plantop_k、命中文档数、检索耗时

task_id、session_id、trace_id 这三层关联标识是我特别想强调的。trace_id 关联单次任务执行链路,像一张“任务过程快照”;session_id 关联同一个用户的多轮对话,用来观察上下文如何累积;task_id 则用来关联业务侧的订单号、工单号等业务实体。我在实际项目里踩过坑:一开始只埋了 trace_id,结果用户来投诉说“昨天那个对话回答错了”,我们对着 trace 查了半天,发现查到了用户昨天的另外一次任务,因为系统把 trace_id 重置了。后来强制要求三个 ID 同时落,业务排查效率高了一个量级。

2.3 埋点实现:一个不污染业务代码的 LLM 调用追踪装饰器

很多团队不乐意做埋点,是因为觉得埋点代码会污染业务逻辑。实际上用装饰器或者中间件可以完全解决这个问题,LLM 调用的埋点尤其适合做在统一出口上。下面这个例子是我在一个 Python 项目里实际用过的简化版,核心思路是:所有 LLM 调用都走同一个网关函数,装饰器在这个函数外自动创建 Span 并捕获 token 用量。

from opentelemetry import trace from opentelemetry.trace import SpanKind from functools import wraps tracer = trace.get_tracer("llm-gateway") def trace_llm_call(provider, model): def decorator(func): @wraps(func) def wrapper(messages, **kwargs): span = tracer.start_span("llm.call", kind=SpanKind.CLIENT) span.set_attribute("llm.provider", provider) span.set_attribute("llm.model", model) span.set_attribute("llm.prompt_tokens_estimate", estimate_tokens(messages)) try: resp = func(messages, **kwargs) usage = resp.get("usage", {}) span.set_attribute("llm.prompt_tokens", usage.get("prompt_tokens", 0)) span.set_attribute("llm.completion_tokens", usage.get("completion_tokens", 0)) span.set_attribute("llm.total_tokens", usage.get("total_tokens", 0)) cached = usage.get("prompt_tokens_details", {}).get("cached_tokens", 0) span.set_attribute("llm.cache_read_tokens", cached) return resp except Exception as e: span.set_attribute("error.type", type(e).__name__) trace.get_current_span().record_exception(e) raise finally: span.end() return wrapper return decorator

这里面有几个细节值得说。第一,在调用前先估算 prompt_tokens,虽然不准,但能让你在模型真正返回前就看到 token 量级的初步信号,对追踪超长请求特别有用。第二,从响应里读取 usage 字段是标准做法,但要注意不同模型服务商的字段结构略有差异,有的放在顶层,有的放在 response_usage 里,网关层要做好适配。第三,缓存读取 token 这个字段太容易被忽略,但很多服务商对缓存 token 和普通输入 token 分别计价,而且差价很大,不单独记录会导致你的成本核算偏差巨大。

2.4 采样策略:元数据全量采集,内容按需快照

Agent 场景的采样策略和传统后端不一样。传统 APM 通常建议概率采样,比如采样 10% 的请求,因为流量大、低价值。但 Agent 请求往往低频高价值——一个任务可能消耗几千上万 token,而且模型行为随机,如果只采样 10%,出问题的那个任务很可能恰好没被采到,留下的都是正常请求,链路诊断失去意义。

我的做法是分层策略:所有 Span 的元数据全量采集,包括模型名、token 数、工具名、耗时、错误类型;但 prompt 内容和模型输出内容默认不采,因为在生产环境里 prompt 可能包含用户隐私或业务敏感信息,全量落盘会有合规风险。

只有当链路诊断需要时,才针对特定 trace_id 开启内容快照。实现上也不难:在网关层设一个开关,命中采样规则的请求把 prompt 摘要存到专门的存储,设置 7 天过期。我甚至见过更细的做法:只存 prompt 的前 200 个 token 和模型输出的前 200 个 token,对大部分问题诊断已经够了,而且把敏感信息暴露面降到最低。用摘要代替全量,这个思路在 Agent 可观测性里非常重要。

3. 链路诊断实战:Token 交换失败与上下文超限的完整排障路径

3.1 案例一:登录链路“token exchange failed”反复出现,怎么定位

Agent 应用里 token 这个词有两层含义,很多人一开始会被绕晕。一层是模型计费用 token,另一层是认证鉴权用 token(JWT、OAuth token)。我在项目里遇到最多的坑是后者:用户登录时控制台报“sign-in could not be completed, token exchange failed”,或者对接外部 API 时偶发“token exchange failed: 400 bad request”。这类报错排查起来特别容易踩坑,因为问题往往不在报错的那一行代码里。

我总结了一套可复用的排查路径,核心就是让链路追踪告诉你“token 交换到底卡在哪一步”。

第一步,先看错误率趋势。打开认证服务的错误率曲线,区分这是瞬时抖动还是持续故障。瞬时抖动大概率是某个基础组件重启或网络瞬断,持续故障才需要深入链路。第二步,在追踪系统里按 trace_id 拉出登录链路的完整 Span 列表,你会看到认证服务调用身份提供商的 Span 标红,展开后能看到 HTTP 状态码、请求 URL、响应体摘要。第三步,根据状态码分流:

  • 400 Bad Request,常见于 refresh_token 为空或格式非法。我在一个项目里遇到过“invalid 'refresh_token': empty string. expected a string with minimum length 1”的报错,最后定位到代码里从本地存储取 token 时,key 拼错了,取到的是 None,不是 token 真的失效。这类问题没有链路追踪的话,只能靠人肉读代码猜。
  • 403 Forbidden,常见于账号所属区域、IP 策略不匹配。这个和代码关系不大,问题在账号配置或网关策略。链路里记录的 provider 名和请求目标 IP 能帮你快速确认是这个原因。
  • 网络层错误,比如“error sending request”,则是 API 不可达,需要检查网络策略、防火墙、域名解析,和 token 本身没有关系。

这个案例里我用“auth.example.com/oauth/token”这种通用形式来举例,实际项目里换成你的真实认证端点即可。

3.2 案例一背后的共性根因:Token 生命周期与续签机制设计

排查完单次故障之后,我会建议团队不要急着关 Issue,因为你很可能碰到了 Agent 长任务场景下最常见的共性问题——token 过期。JWT 和 OAuth access token 一般都有有效期,短则 30 分钟,长则几小时。Agent 任务往往比这更久,一个复杂的调研任务跑十几分钟很常见,如果中间调用了大量外部 API,很可能任务还没跑完,token 已经过期。热词里“jwt实现token续签”被反复搜索,就是因为这个需求在 Agent 项目里特别普遍。

我的建议是三层防护。第一,接入层用双 token 机制,access_token 短时效 + refresh_token 长时效,网关捕获 401 后自动用 refresh_token 续签,续签动作本身也作为一个 Span 被追踪,这样你随时能看出“这个任务中途续签了几次、失败了几次”。第二,在工具调用 Span 里记录 token 剩余有效期,接近过期时提前刷新,避免请求打到一半突然失败。第三,监控 refresh_token 的失败率,因为 refresh_token 一般是长期有效的,如果它频繁失败,说明本地存储有问题或者被服务端撤销了,那就不只是续签能解决的,而是整个会话体系出问题了。

3.3 案例二:单会话 Token 消耗逐轮上涨,最后撞上上下文窗口

第二个案例是这样的:一个客服 Agent 上线三周后,开始出现“context length exceeded”报错,而且用户反馈对话越来越慢。当时团队的第一反应是调大模型上下文窗口,但成本不允许。后来我帮他们看 Token 计量曲线,发现一个规律:prompt_tokens 是逐轮线性上涨的,每轮对话大约增加 1500 token。

顺着这个特征去查 llm.call Span,果然在属性里看到每一轮都把完整历史消息塞进 prompt,没有做任何压缩。客服对话长一点,prompt 里就塞了几万 token,一来慢,二来贵,三来把上下文挤爆。这个根因用链路追踪很好定位:在 Span 属性里新增两个字段,compression_before_tokens 和 compression_after_tokens,分别记录压缩前后的 token 数,再用时序曲线叠加看,一目了然。

修复方案是“滚动摘要 + 滑动窗口”:每轮对话结束时,用一个小模型把历史对话压缩成 300 token 的摘要,只保留最近 8 轮完整对话,加摘要一起进 prompt。上线后观察 Span 属性,prompt_tokens 从 4 万降到 6000,响应时间从 30 秒降到 8 秒,单会话 token 成本下降 70%。

3.4 Token 用量曲线本身就是最重要的健康信号

这两个案例放在一起看,你会发现一个共同点:真正定位问题靠的不是错误日志,而是 Token 用量曲线和链路属性的组合。Token 用量在这个场景里就是 Agent 的“体温曲线”,你不需要理解业务逻辑,单看曲线形态就能发现异常。

我常用的判断规则有这几条:第一,单会话 token 消耗呈线性增长,多半是上下文没有压缩;第二,单任务 token 消耗出现阶梯式跳升,多半是 prompt 模板改动或工具返回异常;第三,错误率没涨但 token 翻倍,多半是重试循环;第四,缓存命中率突然下降,多半是 prompt 前缀被改动,缓存全部失效。这几条规则看起来简单,但真正把它变成监控告警的团队不多,绝大部分是等到账单爆了才回头查。

4. Token 成本精细化核算:从网关计量埋点到业务维度分账

4.1 为什么常规“看账单”式核算根本不够用

很多团队算 token 成本的方式特别粗犷:月底看模型服务商账单,总额多少就记多少。这种“事后总额”完全支撑不了决策。你没法回答三个问题:钱花在哪个功能上?哪个 Agent 技能成本最高?哪个用户烧掉了最多的 token?

我记得有次和一位做 Agent 产品的朋友聊,他说自己也知道成本高,但说不清高在哪,只能无差别地限制所有用户的使用次数。结果把重度付费用户也限了,客户满意度直线下降。精细化核算本质上不是为了算账,是为了让你能“基于成本做决策”:是这个技能价值高值得保留,还是这个技能设计有问题导致成本虚高?没有分账数据,你只能一刀切。

4.2 计费埋点记录什么:一张审计字段表

我的做法是在 LLM 调用网关统一埋点,每个请求生成一条计费审计记录,字段表大致如下。这个表我调整过好几轮,前四类字段是必须的,后面两类是进阶。

类别字段说明
模型信息model、provider用于按模型单价核算
Token 用量prompt_tokens、completion_tokens、total_tokens、cache_read_tokens核心计量数据
业务标签user_id、session_id、trace_id、agent_name、skill_name用于按业务维度分账
性能字段latency_ms、request_time用于联动性能分析
结果字段error_flag、retry_count、finish_reason用于异常识别
进阶字段app_version、prompt_template_version用于定位模板改动影响

特别要强调 skill_name 这个字段,它代表“这次调用是哪个具体技能触发的”。很多团队只记录 agent_name,粒度太粗,一个 Agent 里可能挂了十几个技能,成本差异巨大。按技能分账后你才能真正看到,原来“订单查询”这个技能单次成本是“天气查询”的 20 倍。

4.3 成本如何算:输入、输出、缓存读取要分开计价

计费字段拿到之后,成本计算本身也有一些门道。大多数模型服务商对输入 token 和输出 token 分别计价,而且现在越来越多的服务商支持 prompt 缓存,缓存命中的输入 token 价格远低于普通输入 token。如果核算时不区分这三类,成本会严重失真。

计算公式我建议这样写:

单次调用成本 = 输入token数(未命中缓存) × 输入单价 + 缓存读取token数 × 缓存单价 + 输出token数 × 输出单价

下面拿一个假设的模型服务商价目表举个例子,仅用于演示算法,实际单价请以你对接模型服务商的最新合同或官网价格为准。

计费项单价示例(每百万 token)用量成本
普通输入3 美元8,0000.024 美元
缓存读取0.3 美元20,0000.006 美元
输出15 美元1,2000.018 美元
合计--0.048 美元

同样的调用如果缓存命中率差,把缓存读取的 2 万 token 记为普通输入,成本就变成 0.06+0.018=0.078 美元,偏差超过 60%。所以缓存命中这个字段必须记录,它是成本核算准确性的基石。

4.4 三个高价值分析维度与一个成本黑洞案例

有了明细数据,我建议优先做三个维度的分析。第一个是按会话聚合,找单会话 Token 特别高的异常会话。正常用户的对话平均几千 token,突然出现一个 50 万 token 的会话,大概率是上下文泄漏或者死循环,这是最重要的成本异常信号。第二个是按 Agent 技能聚合,做成本排行。排行 Top 的技能不一定是坏事,但要计算单位成本对应的业务价值。第三个是错误率和成本的联合分析。高错误率配高成本是最危险的组合,意味着系统在重复做无用功。

我实际做过的一个客服 Agent 案例很典型。按会话维度看,平均每会话成本 0.35 美元,看起来完全正常。但按技能拆分后发现,一个“订单查询”技能的单次成本高达 2.1 美元,占了总成本的 42%。再钻取 trace 找到原因:查询时使用了全文检索,Top-K 设为 20,每次把 20 份文档全塞进 prompt,而真正有用的只有 1 到 2 份。调整后把 Top-K 降到 5,引入缓存,迭代了 prompt 模板,单次成本从 2.1 美元降到 0.8 美元,整体成本下降 37%。同样的业务量,省下来的都是利润。

5. 观测大盘的建设顺序与落地工具建议

5.1 别一上来就铺 OpenTelemetry,按这个顺序三步走

很多团队看别人上了分布式追踪,心痒痒,立刻引入 OpenTelemetry 把 Agent 框架的每一个节点都埋一遍。我劝你先冷静一下。全链路埋点改动量巨大,要动业务代码、要部署 Collector、要选存储后端,通常还没看到效果,业务团队就抗拒了。

我建议倒过来,按成本从低到高分三步走。第一步,先做 LLM 调用网关的计量埋点。这一步不涉及业务代码,只需要在统一网关函数里加日志,当天就能上线,当周就能看到 token 消耗成本全景。这笔投资回报率最高。第二步,统一业务日志格式,强制所有 Agent 任务在日志里输出 trace_id、session_id、task_id,让日志服务能够按 ID 聚合。这一步也不需要引入新组件,只是规范日志输出,但能解决 80% 的“根据用户反馈定位问题”场景。第三步,等团队意识到链路追踪的价值后,再逐步引入 OpenTelemetry 做完整 Span 埋点,覆盖 plan、tool、llm 等核心流程。

这套顺序我在两个团队里都实践过,第一阶段通常一两周就能完成,但带来的感知非常强。相比之下,直接铺 OpenTelemetry 的项目,大部分三个星期后还在折腾 Collector,业务方已经失去耐心。

5.2 看板上的核心指标:一张你抄得走的指标清单

观测大盘不用做得很花哨,关键是放对指标。我经过几轮精简,现在团队看板上固定放下面这组指标,每个指标背后都有具体的告警逻辑。

指标计算粒度告警规则示例
请求成功率全任务5 分钟成功率低于 95%
P95 端到端延迟全任务环比上升超 30%
LLM 调用错误率全任务错误率超过 5%
Token 日消耗总量全任务环比上升超 50%
缓存命中率全任务低于 60% 时预警
工具调用失败率按工具单个工具失败率超 10%
单会话 Token 消耗 P95按会话超过阈值触发检查
平均单任务 Token 数按 Agent环比上升超 30%

这里面有两个指标是我用很久之后才意识到重要的。一个是缓存命中率,它直接反映 prompt 模板是否稳定,模板频繁改动会导致缓存大量失效,成本上涨但业务量没涨。另一个是单会话 Token 消耗 P95,相比平均值,分位数更能暴露“最差的那批用户”在烧多少钱。

5.3 几个容易踩的坑和我的应对习惯

最后分享几个我在实践里反复踩过的坑,以及现在养成的应对习惯。

第一个坑:埋点本身拖垮了业务。LLM 调用的响应时间本身就慢,如果你在装饰器里做同步写日志、同步上报追踪数据,等于把慢路径又加长了。我现在一律要求异步上报,日志先写本地缓冲区,后台批量推送,绝不在业务线程里做网络 IO。还有就是要给追踪 SDK 加熔断开关,极端情况下观测系统自身故障不能影响业务。

第二个坑:只埋点不设预算熔断。Token 成本不像服务器费用是相对固定的,一个 bug 可以让成本在几小时内翻几倍。我现在会在网关层设置“预算熔断”逻辑:当某个 Agent 技能的日消耗超过设定阈值时,自动降级到更便宜的模型,或者暂停非核心技能,优先保住核心链路。这个和传统的限流不太一样,它的目的不是保护服务,而是保护钱包。

第三个坑:prompt 模板的版本没有纳入观测。改 prompt 是调成本最快的方式,也是最容易翻车的方式。我把 prompt_template_version 作为 Span 属性和计费字段记录之后,就找到过一次很隐蔽的成本上涨:一个运营同学改了 prompt 里的一个词,导致缓存命中率从 85% 掉到 20%,整体成本涨了 40%。如果没记版本号,这种问题只能大海捞针。

第四个坑:过度采集导致存储成本失控。全量采集元数据听起来很好,但一个 Agent 平台一天可能产生上千万条 Span,存储成本也不便宜。我的习惯是 Span 元数据保留 30 天,内容快照保留 7 天,超过时间的自动清理。可观测性本身也是成本,也要被纳入成本核算,别把监控做成了新的账单炸弹。

做 Agent 可观测性这段时间,我最大的体会是:这个领域还没有像 Web 监控那样的成熟标准,很多方案要自己摸索,但核心思路是清晰的——把 Agent 的执行轨迹和 Token 消耗当作第一等公民来观测。你先从网关计量埋点开始,把成本账算清楚,再逐步加链路追踪和诊断能力,这条路是通的。至于要不要上 OpenTelemetry、选 Jaeger 还是 ClickHouse 当后端,这些都是后话,先把最基本的 trace_id 打通,你就已经比大多数团队领先了。

RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进