
Vibe Coding 这个词最近在开发者社区里出现频率非常高。它描述的是一种新的写代码方式你把需求说清楚AI 把代码生成出来你负责跑、看结果、继续提要求而不是逐行手写。Java 社区里用 Trae、Copilot 和各种 AI 插件写 Controller、Service、Mapper 的开发者越来越多原型阶段的效率确实高得离谱。但问题也跟着来了代码跑通不代表系统可靠。尤其是当 AI 生成的代码进入真实业务调用链变长模型输出接进下游逻辑之后你会发现自己很难回答几个基础问题这个功能为什么最近变慢了用户遇到的报错到底发生在哪一段Prompt 改了一版之后同一个输入为什么出现了两个完全不同的结果Vibe Coding 缺的不是代码量而是可观测性。没有 Observability 的 AI 辅助项目本质上还是一个黑盒你知道它现在大概能用但说不清它是怎么工作的出了问题也没有足够信息去还原现场。这篇文章想聊清楚一件事如何用 Observability 把 Vibe Coding 从“快速原型”推到“AI Engineering”。1. Vibe Coding 的本质生成变快但理解成本转移了1.1 它解决的真实问题是“从零到一”Vibe Coding 的价值不适合被夸大也不适合被贬低。它真正擅长的是把“我大概知道要什么”快速变成“一个能跑起来的版本”。比如你在做一个内部知识库问答服务。以前你要先搭 Spring Boot 项目写实体、写 Mapper、写 Service、写 Controller再对接模型接口一套下来几个小时。现在你把需求描述清楚AI 帮你把骨架代码生成出来剩下的工作是看接口对不对、参数对不对、业务逻辑有没有偏差。这个流程里人的工作发生了迁移从“写代码”变成“描述需求 检查结果 修错误”。生成速度提升了但理解和维护的责任没有消失反而更重了。1.2 代码能跑和系统可维护是两码事AI 生成的代码通常在“单次运行”层面是正确的但在“长期运行”层面是脆弱的。原因有三个。第一没有人完整掌握全局。你可能只看了 AI 生成的那几个文件但没完全理解它调了哪些第三方库、用了什么隐藏约定、依赖了哪个版本的接口。第二模型输出有不确定性。同一个 Prompt 在不同时间可能给出不同答案你无法只靠“刚才跑了一次正常”就得出结论。第三错误信息经常藏在模型返回里。当模型返回的不是纯文本而是 JSON、Markdown 或代码片段时解析层的边界问题很容易变成诡异的线上 bug。这时候你最需要的东西不是更多代码而是“能看清楚系统内部发生了什么”的能力。这就是 Observability。2. AI Engineering 跟 Vibe Coding 的分界线在哪2.1 AI Engineering 不是换个名字有人觉得 AI Engineering 就是把 AI 模型接进系统里代码能跑就可以了。这个理解太浅了。AI Engineering 更像是围绕 AI 应用的可靠性工程模型输出的质量怎么验证调用失败怎么降级上下文长度超了怎么处理单次请求成本怎么控制Prompt 改了以后怎么判断效果是变好还是变差这些问题 Vibe Coding 阶段几乎都不会考虑但进入生产环境后每一个都会出现。2.2 Demo 代码和生产代码的差距我一般会用下面这张表判断一个项目处于哪个阶段关注点Vibe Coding 阶段AI Engineering 阶段代码来源AI 生成人只看结果AI 生成人负责验收、测试、维护判断标准“能跑通”“能重复、能监控、能排查”错在哪大概知道说不清楚有日志、有 requestId、能还原现场Prompt 变更凭感觉改用评测集验证模型服务异常一直等超时有超时、重试、降级和告警成本不管每次调用按 Token 和耗时统计差距的核心不是工具而是你有没有形成闭环。2.3 Java 项目特别容易被忽略的地方Java 生态对生产环境的老牌支持其实很强Logback、Log4j2、Spring Boot Actuator、Micrometer、OpenTelemetry都是很成熟的东西。但 AI 应用引入了一个新维度——模型调用。这个维度跟普通的 HTTP 调用不一样它要记录完整 Prompt、记录原始返回、统计 Token、追踪上下文窗口还要评估输出质量。很多 Java 项目在传统链路监控上做得很好却漏掉了最关键的“AI 调用层”。这是目前最常见的盲区。3. Observability 到底要观察什么3.1 传统三支柱先保住可观测性的基础还是那三样日志、指标、链路追踪。日志记录发生了什么。比如一次模型调用的开始、结束、异常。指标统计趋势。比如请求量、错误率、平均耗时、Token 消耗。链路追踪把一次用户请求从入口到模型调用再到落库的完整路径串起来。先别急着搞复杂平台这三样没做好后面都白搭。3.2 AI 应用额外要观察的五类数据传统系统只需要知道“这次调用成没成功”AI 应用不够至少还要观察输入载荷完整 Prompt、上下文长度、系统提示词版本、有没有敏感信息。模型原始返回成功时模型到底生成了什么失败时错误码和错误信息是什么。Token 与成本输入 Token、输出 Token、单次成本、按用户或按功能聚合后的总成本。耗时拆分网络耗时、排队耗时、模型推理耗时、返回解析耗时。质量信号用户是否点了重新生成、是否拒绝结果、是否触发降级、人工介入次数。这些数据不是用来炫技的而是在出问题时能帮你快速定位“问题出在输入、模型还是解析层”。3.3 输出格式和解析层是最容易被忽略的黑盒很多模型服务返回的都是 Markdown、JSON 或带代码块的文本业务代码再去解析这段文本提取关键字段。这里有一个非常普遍的坑模型语法正确但格式不完全符合预期比如 JSON 里多了一个注释、Markdown 代码块加了语言标识、返回内容里混入了额外说明。这类问题在单次测试时很难发现因为你不完全清楚模型的原始返回长什么样。只有把原始返回记录下来才能快速判断是模型的问题还是解析层的问题。4. 给 AI 辅助项目接入 Observability 的实操路径4.1 第一步统一结构化日志如果你现在还在用log.info(调用模型成功 result)这种写法第一步先改掉。改成 JSON 结构日志带上关键维度MDC.put(requestId, requestId); MDC.put(userId, userId); MDC.put(promptVersion, promptVersion); log.info(llm_call_start model{} inputTokens{} promptLength{}, model, inputTokens, prompt.length()); log.info(llm_call_end status{} outputLength{} latencyMs{} tokens{}, status, output.length(), latencyMs, tokens); MDC.clear();这样做的好处是后续接日志平台、按 requestId 查询、做聚合统计都非常简单。如果项目已经用了 Spring Boot Actuator还可以直接暴露/actuator/metrics和/actuator/health先把基础指标接上。4.2 第二步给模型调用加上 Trace传统 HTTP 调用有 traceId模型调用也要有。推荐的链路结构是这样用户请求 (requestId / traceId) - 业务逻辑 - LLM 调用 span - 记录 Prompt 摘要 - 记录模型名称和参数 - 记录结果状态 - 解析层 span - 记录解析是否成功 - 下游业务 span如果不想自建平台可以先走 OpenTelemetry 的协议上报或者用支持 LLM 可观测的平台。关键是每一条模型调用都必须能关联到具体的用户请求和具体的 Prompt 版本。4.3 第三步把 Token 和成本变成指标Token 数据通常从模型接口的返回里能拿到。把这些值存成指标按时间聚合就能看到几个关键趋势平均每次请求消耗多少 Token哪个用户的调用成本最高哪个功能模块的调用量增长最快上下文长度是否在缓慢增长这些指标直接决定了成本预算和优化方向。比如发现某类请求频繁超长就可以考虑加缓存、压缩上下文或者限制最大长度。4.4 第四步建立回归评测集这是从 Vibe Coding 走向 AI Engineering 很关键的一步也是很多人忽略的一步。做法很简单选一组有代表性的测试输入比如 30 到 100 条典型问题覆盖正常情况、边界情况和易错情况。每次修改 Prompt、更新模型、调整参数之后用同一组输入跑一遍对比输出结果。判断方式可以人工看也可以用另一套标准去自动评分。重点是“变化是可追踪的”不是“我改了 Prompt 感觉更好”。评测集跑出来的差异能让你避免盲目迭代。4.5 Java 开发者的切入建议不管你用的是哪款 AI 编程工具接入可观测性的位置是一样的用 Logback 或 Log4j2 的 JSON 格式输出日志用 Micrometer 把模型调用延迟、Token、错误数暴露成指标在调用模型前设置 MDC 上下文日志里带上 requestId把模型接口的 HTTP 客户端包装一层统一记录耗时和状态优先做第一点和第三点成本最低收益最直接。5. 怎么判断你已经从 Vibe Coding 走到了 AI Engineering5.1 一个验收清单不需要问自己“我的项目工程化了吗”直接回答下面几个问题问题能回答才算工程化用户报了一个错你能在 10 分钟内找到对应的原始 Prompt 和模型返回吗能改了 Prompt 之后怎么证明线上效果变好或变差有评测集和对比记录这次模型调用花了多少钱、多少时间能从指标里查到模型服务超时或返回异常系统会怎样有超时、重试、降级预案同一个输入两次返回不一致你能解释吗能区分是模型随机性还是上下文变化日志里每条 AI 调用能串联到用户请求吗能如果答案大多是“不能”那这个项目还停在 Vibe Coding 阶段。并不是说这个阶段丢人而是你要清楚它的边界适合原型、Demo、内部试用不适合直接面向生产用户大规模使用。5.2 资源有限的时候先做什么小团队、小项目没必要一上来就搭全套平台。我建议的优先级是结构化日志包含 requestId、模型名、Token、耗时、状态。日志带上完整的 Prompt 摘要和模型原始返回至少保留最近几天的量。一组几十条的评测集每次改 Prompt 都跑一遍。模型调用失败时的降级处理比如返回兜底内容或提示用户稍后再试。这四件事做完你已经比绝大多数 AI 辅助项目更接近工程化了。后续再考虑告警、看板、成本报表。5.3 不要一次全上可观测性是一项长期建设不是一次性装修。一次把所有指标接完的做法反而容易因为数据太多没人看而荒废。更好的节奏是每次遇到一个线上问题就补一项观测能力。出过什么问题就记录什么数据。这样建设出来的观测体系每一层都跟真实业务绑定。6. 常见误区和排查链路6.1 误区一日志记了一大堆但没法定位很多人以为日志越多越好。实际上如果没有统一的 requestId 和结构化字段日志多只是增加噪音。排查时要从入口拿到 requestId然后按 requestId 过滤所有日志才能快速看到一次请求的完整路径。6.2 误区二只看最终结果不看原始返回最典型的例子模型返回了一段带着 Markdown 标记的 JSON解析失败接口报错了。很多人第一反应是“模型不行”但看一眼原始返回就会发现问题出在解析层没有处理代码块。没有原始返回记录这个问题排查起来会浪费大量时间。6.3 输出异常时的排查顺序如果遇到“AI 结果不对”的问题我一般按这个顺序查看输入Prompt 是不是被截断了、上下文是不是超长、系统提示词是不是被覆盖了。看模型原始返回模型到底生成了什么有没有被格式影响。看解析层解析代码是否适配了所有返回格式。看下游解析成功后的数据有没有被后续逻辑修改。看模型配置temperature、max_tokens 这些参数是否合理。这里有个经验很多“AI 输出错误”最终都落在第 3 层也就是解析层。因为模型本身可能没写错只是格式和你解析代码的预期不一致。先在日志里看原始返回再判断是哪一层的问题不要一上来就怀疑模型。6.4 请求变慢时的排查方向先看日志里的耗时拆分。如果网络耗时大可能是服务商或网络问题如果排队耗时大可能是并发打满了如果推理耗时大可能是输入上下文太长或者模型太重如果重试次数多可能是间歇性超时加退避策略不合理。6.5 成本异常增长时的排查方向先按 Token 消耗做排行找出最贵的用户、最贵的功能模块。再看是否有人把长文档一次性灌进去或者输出 Token 没有限制或者缓存命中率太低。成本问题通常不是模型本身贵而是调用方式不对。7. 几条实战建议让可观测性真正落地7.1 从最小闭环开始不要先搭平台很多团队一上来就想搭一套完整的可观测平台结果平台建好了业务数据却没接好。我更推荐反过来先在模型调用这一层把结构化日志写出来把 requestId 和 Token 记下来。数据有了后面接什么平台都容易。7.2 把评测集当成代码的一部分评测集应该跟着项目走存在同一个仓库或同一个文档系统里。每次改 Prompt、换模型、调参数都要跑一遍评测集。如果团队有 CI甚至可以把评测集做成自动化的回归任务防止问题重现。7.3 对模型输出保持防御心态模型不是数据库它的输出可能有格式偏差、内容幻觉、中途截断。任何接进业务逻辑的模型输出都要做格式校验、内容校验和异常兜底。不要假设“模型这次返回的一定是合法 JSON”。7.4 观察成本与观察质量同样重要很多人的第一反应是关注准确率但实际生产里成本失控比准确率下降更致命。每天看一次按功能模块聚合的 Token 消耗能帮你提前发现异常调用模式也能帮你判断是否需要引入缓存、缩减上下文或调整模型规格。7.5 回到本质Vibe Coding 适合探索适合做原型适合让开发者把精力放在更高层的问题上。但代码可以交给 AI 写系统能不能上线标准不能降。Observability 就是那座桥把“代码能跑”升级成“系统可用、可排查、可度量”。从一条结构化日志开始慢慢补全AI 辅助项目也能具备工程级的可靠性。