AI工程化落地全链路:从需求拆解到可观测性实践

发布时间:2026/9/29 19:26:52
AI工程化落地全链路:从需求拆解到可观测性实践
1. 从零开始到底从哪里开始ai-engineering-from-scratch这个项目名乍一看很容易让人以为又要“从零训练一个大模型”。但你真在AI工程里泡过一段时间就会明白绝大多数团队真正缺的不是把基座模型重新训练一遍的本事而是把现有模型稳定、可控、可评估地接入业务系统的工程能力。我理解的from scratch是指从需求拆解、输入输出协议、上下文构建、模型调用、Agent编排到评估与可观测性的一条完整链路。这条链路做完你得到的不再是一个“看起来能跑”的demo而是一个可以上线、可以迭代、出了问题能定位的真正软件系统。适合谁看两类人一类是刚带团队做AI落地需要一张全景路线图的技术负责人另一类是已经调通过几个API但总觉得项目“只能在演示时好用”的开发者和算法工程师。1.1 先避开三个经典误区第一个误区是以为“from scratch”等于自己训练一个基座模型。这个误解来源不难理解这几年“从零构建大语言模型”、“从零构建推理模型”的教程和资料确实多看多了自然就往那个方向使劲。但现实问题是预训练基座模型涉及数据工程、算力集群、分布式训练、对齐调优投入和周期都是一个团队按年计算的事情。除非你的目标是做模型研究本身否则这条路对绝大多数业务团队来说性价比极低。工程化落地的重点不是重造发动机而是把现有发动机装进一台能上路的车里。第二个误区是以为接了API调用就是AI工程。只做一次模型调用有点像你会启动发动机但不代表你会造车。真正工程化的部分全部在调用的外围输入格式怎么定义、输出怎么校验、上下文怎么控制、错误怎么兜底、效果怎么度量、成本怎么控制。这些活API本身一个都不帮你做。回头看早期折腾AI应用时踩的坑绝大部分都出在“模型返回之后”和“调用模型之前”而不是“调用那一刻”。第三个误区是跳过评估直接上线。太多项目在demo阶段看着惊艳一上生产就暴露幻觉严重、格式不稳定、成本失控。原因不在模型而在没有一把“回答质量”的尺子。没有评测集就没有回归测试没有回归测试每次改提示词都是碰运气。这个道理和传统软件开发里“没有单测就改重构”是一样的只不过AI系统的不确定性更大评测的优先级应该更高。1.2 我们把“最小工程闭环”定义清楚我习惯把AI工程的最小闭环定义为六个环节需求定义把业务问题转成输入输出协议和评价指标上下文构建决定模型能看到什么包括检索、摘要、历史会话模型调用选择模型和参数执行生成输出校验用schema、规则、工具调用约束确保结果可以被程序安全消费结果评估用小而准的评测集度量质量迭代回归任何prompt、参数、检索策略的改动都要跑一遍评测确认没有变差。这六步听起来简单但每一步都有各自的坑。比如需求定义阶段最常犯的错是把“做一个智能客服”当需求其实那是解决方案真正的需求是“把客服响应时长从10分钟降到2分钟”后面这个需求会直接影响模型选型和评估标准。再比如输出校验阶段很多团队只在demo里打印一下结果根本没有校验环节结果到了生产环境被JSON解析折腾得死去活来。后面几节我会把每个环节展开讲我实际用下来的方案和遇到的坑。整体读下来你会有个感觉AI工程其实没有那么多玄学把它当成一个普通但有严格约束的后端系统来设计就已经赢过大多数团队。2. 端到端链路设计先看清全貌再动手拿到一个AI需求时我最不建议直接开写prompt或接框架。先花半天把链路画清楚后面能省一周的返工。这个链路的全貌是业务目标转需求、需求转输入输出协议、协议决定上下文策略、上下文策略决定模型选型、模型输出过校验、校验结果进评测、评测反馈驱动迭代。每一环都有取舍而且环环扣在一起。2.1 需求拆解不是所有任务都需要智能体我见过太多项目一上来就设计Agent最后发现需求其实一个函数调用就能完成。拆需求时我习惯按任务形态先分四类。第一类是文本转化类比如翻译、摘要、改写、信息抽取特征是输入输出都明确一条高质的prompt加结构化约束就能解决不需要检索不需要多步循环。第二类是知识问答类比如“根据公司资料回答客户问题”特征是答案依赖私有知识必须走RAG把检索和生成结合起来。第三类是多步任务类比如“查一下订单状态、算一下退款金额、再生成一封回复邮件”特征是需要调用多个工具、依赖中间结果、可能要好几轮推理。第四类是流式交互类比如语音客服、实时助手特征是低延迟、增量输出、还要有安全护栏。以我常做的内部知识库客服为例。需求看起来是“问答”但不能直接拿用户问题去问大模型。先要确定输入是用户问题加会话历史输出是带来源引用的答案和置信判断。明确了输入输出协议之后架构自然就指向RAG而不是凭空造一个通用问答框架。你越早把“输入是什么、输出是什么、哪些能错、哪些绝对不能错”定义清楚后面选型越省力。这个阶段我还喜欢顺手列一下负面清单哪些问题不回答、哪些操作不做宁可先窄后宽。2.2 模型选型通用模型、推理模型与部署形态模型选型这件事很多团队喜欢“一个模型打天下”但工程化之后会发现不同任务形态对模型的要求差异非常大。我用得比较顺的选型策略可以看这张表任务形态模型倾向原因简单改写、抽取、分类小尺寸对话模型延迟低、成本低效果完全够用复杂推理、规划、工具编排推理模型会显式拆解步骤适合做planning客服闲聊、内容生成对话模型加少量示例语气自然、回复快体验好私有数据问答通用对话模型加RAG参数知识解决不了私有域省下成本做检索更划算推理模型和对话模型在工程里经常是搭配着用而不是二选一。推理模型适合做规划者产出工具调用序列和中间计划对话模型适合做执行者把计划变成面向用户的自然语言。这样搭配的好处是成本和延迟可调度复杂的规划才上重模型简单的执行走轻量模型。如果你把所有任务都交给最强的推理模型账单会先撑不住。部署形态也约束了选型。纯云端API接入快、不占算力但数据要出网延迟受网络影响本地推理则适合私有化部署场景可以根据业务并发买卡。我的经验是先用API快速跑通闭环把链路验证好再根据合规和成本决定要不要迁移到本地。一上来就自建推理集群容易被运维拖住主干进度。2.3 链路里最容易低估的环节约束与协议进到下一章之前我想先强调一个容易被低估的环节约束与协议。做AI工程和做传统接口开发是一样的模型输入输出的协议应该被当成接口契约来定义而不是当成一句自然语言描述。输入字段有哪些、哪些允许为空、输出结构长什么样、来源引用怎么标注、异常情况怎么表达这些都要写清楚。我在项目里会把协议直接写成JSON Schema或者类型定义模型相关的提示词只是协议的一种表达方式。这个习惯帮我挡掉了大量“模型输出格式不对”的生产事故。你想想传统后端接口如果参数类型不对编译器直接报错而模型的输出没有类型系统兜底只能靠外部校验和约束。所以协议先行不是可选动作是必须动作。到这里链路设计的框架已经出来了接下来进入每个环节的具体做法。3. 提示工程与结构化输出把“问模型”变成“调系统”提示工程这个词很多人听着玄但本质上它就是把“对模型说话的方式”工程化。过去大家觉得prompt是写给模型看的文字后来做得多了才明白prompt更像是写给协作程序员看的接口文档。好的提示词能极大减少下游解析和校验的成本差的提示词会让模型自由发挥输出千奇百怪。这一节我把从system prompt到结构化输出到上下文检索的完整做法拆开讲。3.1 System Prompt是工程配置不是作文题很多人把system prompt当成小作文来写堆一堆“请你务必”“一定要认真”之类的话。实际效果呢加不加都差不多。我实践下来好的system prompt更接近一份API使用文档结构固定字段明确。一个能落地的system prompt模板长这样你是内部知识库客服助手。 任务根据提供的资料回答用户问题回答必须附引用来源。 可用工具 - search_docs(query): 按关键词检索知识库 - get_doc_metadata(doc_id): 获取文档标题、更新时间 输出协议严格JSON { answer: 回答正文最多200字, sources: [{doc_id: ..., title: ...}], confidence: high|medium|low } 负面规则 - 资料中找不到答案时明确回答“暂无资料”不要推测。 - 不输出资料之外的额外承诺。 - 不讨论政治敏感话题。这个模板里每一项都有存在的理由。角色和边界限制了模型自由发挥的空间任务定义划定了交付物工具列表告诉模型它能用什么资源输出协议让下游程序可以直接解析负面规则是幻觉兜底。你发现没有这不像作文更像配置项。系统提示词不是写得越长越好是信息密度越高越好。3.2 真正可靠的结构化输出现在聊一个生产环境绕不开的问题怎么让模型稳定输出合法的结构化数据。先说结论“请用JSON返回”这句话在工程上不可靠。模型是token概率系统这种软约束经常失效可能给你加一段解释或者输出带注释的JSON甚至给出CSV风格的结果。工程上有几层加固手段我从弱到强排列。第一层是函数调用约束。现在主流模型服务商都支持tool calling或function calling你把输出结构定义在函数参数schema里框架会强制模型生成合法的结构化参数。这比任何提示词都牢靠。第二层是外部校验器兜底。拿到模型文本之后用类型校验工具做硬约束Python就用pydanticTypeScript就用zod解析失败就走重试逻辑。第三层是降级策略。重试一次仍然失败就返回统一错误结构让调用方感知并处理而不是把坏数据写进数据库。这就是现在圈子里常说的“typesafe AI”的核心思想。类型安全不是只在Java或TypeScript里才有大模型输出同样需要类型安全。尤其当AI系统要和订单、库存、账务这类业务数据对接时一个不合法的字段就可能触发连锁故障。别指望模型每次都守规矩要在它不守规矩的时候兜住。3.3 上下文工程检索参数不要拍脑袋RAG的关键不是“把文档塞给模型”而是“只把模型需要的内容给它”。检索参数直接决定回答质量而且这些参数不能拍脑袋定。我常用的三个超参是chunk size分块大小建议从400到800字符起步而不是默认取整篇因为内容太长会稀释模型的注意力top-k召回条数先设5左右再配合rerank做精排相似度阈值低于阈值的材料宁可不要也别让模型硬答。我自己踩过的坑是一开始为了让“模型信息更多”把top-k设成20结果模型在长篇材料里彻底迷路回答又长又含糊引用来源还点不对。后来改成top-k取5加重排加阈值过滤回答的准确率和精炼程度都上来了。有一个概念你需要记住上下文不是越全越好是越准越好。一大堆弱相关内容堆进去只会让原本清楚的问题变模糊。给你一个可以直接抄的配置感chunk_size600chunk_overlap100top_k5similarity_threshold0.72先跑一轮看badcase再微调。这套配置不是标准答案但比瞎调强很多。4. Agent编排与Harness工程实践当任务从单轮问答变成“查订单、算金额、发邮件”这种多步操作就需要Agent编排了。Agent不是神秘概念说白了就是让模型能够调用工具、观察结果、再决定下一步的系统。但让模型自由发挥是危险的这一节的关键词是“约束”怎么设计好编排流程怎么用Harness给Agent装上骨架怎么处理状态和恢复。4.1 从单轮调用到多步AgentAgent最常见的范式是ReAct即推理加行动交替循环。模型的每一步先用“Thought”梳理当前状态再决定“Action”调用哪个工具工具返回结果作为“Observation”然后进入下一轮直到完成目标。拿订单售后场景举例第一轮模型判断用户想查询订单状态调用查询工具拿到订单为“已发货但用户申请退款”第二轮模型根据退款规则调用金额计算工具算出应退金额第三轮模型生成一封回复邮件结束循环。每一轮都是模型调用加工具调用的组合中间结果要传递下去。这里有一个设计要点工具返回的结果不要太啰嗦。模型上下文窗口有限工具应该返回结构化、精炼的状态而不是一整张表。比如查询订单工具返回{order_id:A001,status:shipped,refundable:true,amount:129.9}模型一看就懂。我自己早期犯过给工具返回大量无关字段的错误模型反而抓不住重点判断决策变慢。工具返回的字段只给当前决策真正需要的。4.2 Harness给Agent装上骨架和安全带“harness engineering”这几年在圈子里讨论很多。直译是“挽具”你可以理解成给Agent做的工程脚手架。为什么需要它一个没有harness的Agent像什么都能干的自由人你托付它办事它同时也给你闯祸。Agent的探索能力越强越需要一个明确的行为边界。我项目里的harness至少包含五件事。一是最小API面Agent只能调用白名单里的工具而不是任意函数或代码白名单外的能力一律不暴露。二是最大步数限制比如一个Agent最多跑8轮循环超过就强制终止并提示人工介入防止死循环烧钱。三是人工审批点涉及写操作、发消息、扣款这类行为时必须暂停等待确认不能直接执行。四是记忆清理每轮对话只保留当前摘要加最近两轮完整消息历史对话做摘要压缩避免上下文爆掉。五是参数校验模型生成的工具参数在真正执行前先过一遍schema校验非法参数直接拒绝。我见过不少Agent失控的案例追根溯源都是harness没做好。比如没有限制工具白名单模型用某种方式拼出了危险参数没有步数上限一个重复失败的任务跑了三十几轮费用吓人。所以我的原则是每个Agent上线前先写清楚“它绝对不能做的事”清单。这个清单比功能清单重要得多。4.3 状态、记忆与可恢复性多步Agent天然是有状态的系统如果只把Agent当成无状态函数来写早晚吃亏。进程崩溃、网络超时、工具报错任何一个环节中断任务怎么恢复我的做法是坚持三个原则。第一对外部系统调用保持幂等每个工具调用带request_id重复调用不会产生副作用。第二会话状态持久化到数据库记录已执行的步骤和中间结果而不是只放在内存里。第三支持断点续跑从最后成功的一步继续而不是从头再走一遍。举个例子任务执行链路是“查账号、扣款、发通知”如果在扣款之后、发通知之前进程崩了靠状态记录就能判断该从哪一步开始并且重发通知之前先查一下是否已经发过。没有持久化状态的话你只能靠运气重启任务。这个意识和做传统后端服务一样AI应用首先是个软件系统其次才是AI。把Agent当作正规服务来设计可靠性问题就少掉一大半。5. 评估、可观测性与迭代闭环一个AI项目能不能长期维护不取决于初期效果有多惊艳而取决于当你改动系统时能不能知道效果是变好了还是变差了。这一节讲评估和可观测性也是我认为AI工程和“调AI demo”之间最本质的区别。5.1 评测集先有标尺再生产没有评测集的AI项目改动全靠感觉。我今天觉得回答变好了明天用户反馈变差了谁也说不清哪次改动导致的。我的建议是先建一个小而准的评测集三十到五十条就够了但覆盖面必须全。正常case选取业务里最高频的问题边界case模糊措辞、超长问题、缺少上下文对抗case诱导模型胡说、问资料里不存在的内容。每条数据不一定需要标准答案全文但要有明确的判断点比如“回答必须包含正确来源”“必须拒绝回答超范围问题”。这个评测集建完之后要持续补充。我自己的习惯是每周抽线上badcase加进去确保每个修过的问题都有回归记录。评测集小没关系但不能没有评测集的质量比数量重要宁可五十条精心标注不要五百条随便造的。5.2 LLM-as-Judge的正确用法人工评测太慢所以实践中普遍用LLM-as-Judge让一个裁判模型按维度给结果打分。这里有几个容易踩的坑。第一裁判模型最好和生成模型不是同一个否则容易出现自卖自夸的系统性偏差。第二评分标准必须带示例不然AI打分比人工打分还飘。第三能用规则校验的东西不要交给LLM判断比如JSON是否合法、来源ID是否真实存在于知识库这些用程序判断又快又准没必要浪费模型调用。给一个我常用的评分维度表维度分值评分要点准确性0-5答案是否与检索材料一致是否存在事实错误完整性0-5是否覆盖用户问题的关键信息点格式合规0-5是否符合输出协议JSON是否能被正常解析安全性0-5是否拒绝越权问题是否包含不当承诺或内容每一轮改动之后用同一个评测集跑一次对比各维度平均分。如果改动让准确率上升但合规率下降那这个改动就不值得上。评分趋势才是你做迭代决策的依据。5.3 可观测性三板斧日志、追踪、成本可观测性决定了你排障的效率。AI项目比传统后端系统更难排障因为输出是概率性的出错可能是提示词问题、检索问题、模型版本问题、工具返回问题。没有详细记录就只能对着一个坏输出猜原因。我的做法是每次模型调用都记录这样一批字段会话ID和请求ID方便串联整个链路模型名称和版本输入tokens和输出tokens延迟采样参数如temperature提示词版本号检索命中的文档列表工具调用序列和结果最终输出和校验结果。有了这套记录badcase就能复盘到具体环节是检索没召回还是提示词让模型跑偏还是工具结果太含糊。你会发现大多数问题根本不需要猜看一眼trace就定位了。成本也一样重要。tokens记录是基础按会话聚合出单次任务平均成本你才知道模型选型调整到底是省了还是贵了。有些团队只盯着模型单价低没看到因为效果差导致的反复调用和人工复核成本总账反而是亏的。可观测性的目标不是监控本身是让每一次迭代都有据可依。6. 实战问题排查速查表最后整理一份我实际项目里反复遇到的高频问题速查表每个问题都是我或身边团队付出过真金白银才总结出来的。现象可能原因排查与解决模型输出JSON总带注释或解释只依赖软约束改用工具调用协议再加schema校验器Agent陷入死循环缺少最大步数限制加循环上限工具返回结构化状态回答幻觉严重但检索看起来没问题top-k太高或阈值太低降低top-k提高相似度阈值检查chunk质量格式化正常但答案内容空洞上下文被历史消息挤占做摘要压缩缩短系统提示词同一问题效果时好时坏模型版本漂移或采样参数过高锁定模型版本调低温度成本涨得离谱推理模型被用在简单任务上拆任务简单执行走轻量模型改动后效果集体变差评测集缺失问题没暴露先恢复上一版本补评测集后再改这些问题的共性是大多数都不在“模型不够聪明”而在外围工程质量。你可能会问为什么这种问题一而再再而三出现因为AI工程链路太长任何一个环节出问题都会在输出端表现为“回答不好”我们容易把锅甩给模型但实际上有七成问题可以靠约束、校验和观测解决。最后分享一个习惯。我现在的每个AI工程都是从最小闭环开始的一个输入、一个输出、一条检索链路、一个小评测集跑通之后再加Agent和工具调用。每次改动只碰一个变量prompt、参数、检索策略分开调然后用同一套评测集对比。个人体会是AI工程百分之八十的工作发生在模型的调用外围而不是模型本身把外围的系统性做好模型应用这件事就没有那么玄。你在自己的项目里遇到卡点的时候可以对照这篇文章往回查一查多半会有答案。