Skip to content

第 2 章 四阶认知:从 Prompt 到 Loop

传统程序员切入 Agent 工程,认知会经历四个阶段。这不是什么理论框架,是我自己走过的路,也是我观察到的绝大多数人卡住的地方。

开篇:所有人都从调 prompt 开始

如果你观察一群刚接触 Agent 的程序员,会发现一个高度一致的模式——大家的第一反应都是研究 prompt。

这很正常。Prompt 是最显眼的旋钮,转一下就有反馈,调一句就有变化。新手最自然的动作就是往 prompt 里加规则、加约束、加示例,然后跑一遍看效果。我自己也是这么开始的,第 1 章讲的那三天调 prompt 的经历就是明证。

但问题在于,很多人会卡在这一步

我见过不少工程师,做了好几个月 Agent,聊天的话题还停留在"你用的什么 prompt""能不能分享下你的 system prompt"。他们的认知模型是这样的:Agent 好不好 = prompt 写得好不好 + 模型选得准不准。

这个模型没错,但它只覆盖了整件事的一小块。Prompt 是起点,不是终点。 从 prompt 往外走,还有三个层级在等着你,而且越往外,越是 Agent 工程的真正核心。

这一章,我想把这条路径画清楚。不是为了让你们按部就班地"升级",而是为了让你知道——如果你现在卡住了,卡在哪一阶,下一阶是什么。

四阶是什么

我先给个全景,然后逐阶展开。

阶段关注点典型问题成熟标志
阶 1 Prompt怎么跟模型说话"怎么写 prompt 让模型听话"会写示例、能控制输出格式
阶 2 Context给模型什么信息"模型需要哪些上下文才能决策"会分层注入信息、管理上下文窗口
阶 3 Harness模型怎么跟系统交互"工具怎么设计、错误怎么返回"工具描述当 prompt 写、错误信息可操作
阶 4 Loop执行循环怎么设计"用状态机还是自决循环、触发和响应怎么分"知道"保持循环简单,复杂度下沉"

你可以把它理解成关注点"从模型逐渐外移到系统"的过程。阶 1 你盯着模型本身(怎么跟它说话),阶 4 你已经在设计整个系统的骨架(循环怎么转)。中间两阶是过渡。

有一点要提前说清楚:这四阶不是"低级到高级"的鄙视链。 你不会因为进了阶 4 就不用管 prompt 了——阶 1 的能力是后面所有阶的基础。四阶的意思是,你的关注范围在扩大,从只盯着 prompt,扩大到同时关注 context、harness、loop。

阶 1 Prompt:大多数人出发,也大多数人在此止步

第一阶不需要多讲——调 prompt。怎么写指令模型才听,怎么给示例模型才准,怎么控制输出格式。

这一阶有一个明确的成熟标志:你不再依赖"说漂亮话"来让模型听话,而是学会了用结构化的方式跟它沟通。 具体来说就是会写示例(术语叫 few-shot,第 1 章解释过),会明确指定输出格式("请输出 JSON,字段包含……"),会在 prompt 里区分"必须遵守的规则"和"参考信息"。

为什么大多数人卡在这一阶?因为 prompt 的反馈太即时了。你改一句,跑一遍,马上看到效果,这种即时的掌控感会让人上瘾,也会让人产生一种错觉——"只要 prompt 调得够好,Agent 就没问题"。这个错觉会把你锁死在阶 1。

阶 1 有一个不那么显眼但很重要的成熟标志:你开始把 system prompt 分区写,而不是平铺。下面是我项目里 system prompt 的真实结构:

markdown
# 行为准则(硬性约束)
- 默认不主动回复,只在被直接提及时才响应
- 以下情况可以主动回复:有人问问题、有人约活动、有人提到费用...
- 以下情况不要回复:纯问候、确认消息、与社区无关的闲聊...

# 什么该保存为记忆(规则 + 反例)
- 保存:确定的计划、费用记录、关于成员的事实
- 不保存:闲聊、问候、天气、"明天几点出发"这类待定信息

# 输出风格
- 结论先行,不要描述你的操作过程
- 操作确认要简洁:做了什么 + 一句话确认

注意这个结构——它把"必须遵守的规则"(行为准则)和"参考信息"(输出风格)分开了,而且每条规则后面都跟了反例("不保存:闲聊、问候")。这些反例不是一开始就有的,是踩了坑之后一条条加上去的。好的 prompt 不是写出来的,是从错误里长出来的。

打破阶 1 的错觉,第 1 章已经讲过方法了:当你发现 prompt 怎么调都调不好的时候,往 prompt 之外看。

阶 2 Context:给模型正确的信息,比给模型正确的指令更重要

往 prompt 之外看的第一站,是 Context。

Context 是什么?就是模型每次做决策时,能看到的所有信息。它包括你写的 system prompt,也包括用户消息、历史对话、工具返回的结果、从数据库里检索出来的资料。所有这些加在一起,构成模型那个瞬间的"视野"。

我意识到 Context 的重要性,是因为一个很具体的困扰:我的 Agent 偶尔会"健忘"。明明上一步刚查过某个信息,下一步它就忘了,重新查一遍。明明历史对话里说过一个关键约束,它到了后面就开始忽略。

一开始我以为又是 prompt 的问题,于是在 system prompt 里加规则:"注意参考历史对话""不要重复查询"。没用。因为这些规则是"提示"模型要记住,但模型实际能看到的历史信息,可能早就被截断或者淹没在无关内容里了。

问题不在"提示它记住",在"它到底能看到什么"。

这就是 Context 层面的事。阶 2 的核心认知是:模型的决策质量,取决于它在决策那个瞬间能看到什么信息。 这跟你给它的指令写得好不好是两回事——指令是"告诉它怎么做",context 是"让它看到什么"。一个瞎子,你指令写得再清楚,他也走不了路。

阶 2 的成熟标志是:你开始主动管理模型的视野。哪些信息该放进上下文、哪些该丢掉、以什么顺序放、历史对话留多少截多少、检索回来的资料怎么压缩——这些才是你花时间琢磨的事。Prompt 从"唯一重要的东西"变成了"context 的一部分"。

讲个真实的例子。我的 Agent 有一项功能是调用外部工具执行耗时任务(要一两分钟),任务完成后回调通知 Agent。但回调的时候,模型已经"失忆"了——它不记得自己当初为什么要启动这个任务,因为那段对话早就被新的消息挤出了上下文窗口。

光靠 prompt 解决不了这个问题——你写"请记住之前的任务"也没用,因为它真的看不见了。我的解法是在回调时往上下文里注入一段恢复提示,主动告诉模型"你正在处理一个刚完成的任务,请先读取任务计划文件恢复上下文"。同时把任务计划写进一个文件,让模型自己去读。

具体到代码层面,我的上下文是分层组装的——不是把所有信息一股脑塞进去,而是分成五层,每层一个独立的消息:

go
func (b *PromptBuilder) Build(ctx BuildContext) []Message {
    msgs := []Message{
        SystemMsg(b.systemPrompt),                              // ① 静态系统提示
    }
    if len(ctx.Projects) > 0 {
        msgs = append(msgs, SystemMsg(b.buildProjectContext())) // ② 活跃任务
    }
    if len(ctx.Memories) > 0 {
        msgs = append(msgs, SystemMsg(b.buildMemoryContext()))  // ③ 检索到的记忆
    }
    msgs = append(msgs,
        SystemMsg(b.buildDynamicContext()),                     // ④ 社区动态 + 近期消息
        b.buildUserMessage(),                                   // ⑤ 当前用户消息
    )
    return msgs
}

你看,系统提示、任务信息、记忆、动态上下文、用户消息——每一层都是独立注入的,有就放,没有就不放。这不是 prompt 调出来的,是 context 层面的工程设计。阶 2 到了这一步,你已经在做"信息架构"了,而不只是"写指令"了。

阶 3 Harness:模型和系统怎么交互

第 3 阶是这份手记花最多笔墨的地方——第 4 章讲工具设计,本质上就是在讲 harness。

Harness 是"模型之外的一切"。阶 1 你管模型(prompt),阶 2 你管信息(context),阶 3 你管模型和系统之间的交互接口(harness)——工具怎么定义、工具返回什么、工具失败了怎么办、工具之间的依赖关系怎么表达。

这个阶段的认知转变是最剧烈的,因为它彻底改变了你看待"接口"的方式。传统程序员把 API 文档当"给人看的说明",到了阶 3 你才明白,工具接口是给模型看的 prompt。工具描述里漏一句话,效果等同于 system prompt 里漏一句话。

阶 3 的成熟标志,第 4 章已经详细讲过了:工具描述当 prompt 写、错误信息要可操作、返回值要包含模型下一步需要的信息、工具间的依赖关系要显式表达。这里不重复。

我只想补一个观察:阶 3 是传统程序员优势最大的地方。 因为 harness 的本质是系统设计——接口设计、错误处理、数据流转——这些全是传统软件工程的看家本领。很多程序员在阶 1 和阶 2 觉得 Agent 工程"很新、很玄",到了阶 3 会突然有种回到主场的熟悉感。你之前写的那些分层架构、错误处理中间件、API 设计规范,全都能用上。

具象一点。拿"错误处理"这件事来说——传统程序里,一个 API 出错了,你返回一个错误码或抛一个异常,调用方(人 or 上层代码)来处理。但在 Agent 时代,调用方变成了模型,事情就不一样了。我在项目里把工具错误分成了四层,每层交给不同的"责任方"处理:

工具执行出错

    ├── Transient(瞬时错误)
    │     网络、限流、超时
    │     → 机制层自动重试(模型根本不知道出过错)

    ├── LLM-recoverable(模型可自修正)
    │     参数格式错、缺少必填字段、路径不存在
    │     → 错误信息回灌给模型,它自己改了重试

    ├── User-fixable(需要用户介入)
    │     权限不足、API Key 未配置、数据未同步
    │     → 中断执行,告诉用户该做什么

    └── Unexpected(未预期异常)
          代码 bug、数据库连不上
          → 上抛异常,记日志,开发者来查

这个四层分流,就是 harness 的核心工作之一。你看每一层的"责任方"都不一样——瞬时错误归机制层(重试),可自修正的错误归模型(改了重试),需要人介入的归用户,彻底崩了的归开发者。这不是 prompt 能做的事,也不是循环能做的事,纯粹是接口设计的功夫。

而每一层的处理质量,取决于你的 harness 设计得好不好。比如第二层"LLM-recoverable"——如果工具返回的错误信息是"参数错误"三个字,模型改不了;如果是"日期格式错误:你输入了'明天',请用 YYYY-MM-DD 格式",模型立刻就能改。这个差别,就是第 4 章讲的"错误信息要可操作"。

这就是阶 3 的本质——你不再只是跟模型说话,你在设计模型运转时面对的整个接口世界。 工具怎么定义、返回什么格式、出错时谁来解决,每一项都是你能掌控的工程设计。

阶 4 Loop:循环要简单,复杂度下沉

最后一阶,也是这份手记第 5 章的主题。

当你把 prompt、context、harness 都搞定了,最后一个问题是:这些东西怎么串起来?模型按什么流程去决策、调工具、拿到结果、再决策? 这就是 loop(执行循环)。

阶 4 的核心认知是第 5 章那句反复出现的话:保持循环简单,复杂度下沉到工具和提示词。

这句话听起来是个设计原则,但它背后藏着一个更深的认知转变:你要相信模型能自己做流程决策。

这个"相信"对传统程序员来说特别难。我们习惯了把流程写死——先做 A,再做 B,如果 C 就跳到 D。这是确定性思维的本能。但阶 4 要求你放下这种本能,把"下一步干什么"的决策权交给模型,自己只负责设计好工具(让它有能力决策)和护栏(让它不会跑飞)。

不是所有的流程都能交给模型——第 5 章讲过,确定性流程该用状态机就用状态机。但对于"需要模型判断"的那部分,你要学会放手,别在代码里替它做决定。

阶 4 的成熟标志是:你开始质疑"我的循环是不是太复杂了"。当你发现自己写的 Agent 越来越像一个庞大的状态机,而且每个状态都有复杂的跳转条件时,你会停下来想——这些跳转,是不是本来应该让模型自己判断的?

下面是我项目里真实的循环结构,用流程图画出来你会看得更清楚——"简单循环 + 显式护栏"长什么样:

消息进来


┌──────────────────────────────────────────────────┐
│  Phase 1 · 构建上下文                              │
│  (系统提示 + 记忆 + 动态上下文 + 用户消息)        │
└──────────────────┬───────────────────────────────┘

┌──────────────────────────────────────────────────┐
│  Phase 2 · ReAct 循环  (最多 N 轮)                │
│                                                    │
│    ┌─────────────┐                                 │
│    │  模型决策    │◄──────────────────┐            │
│    └──────┬──────┘                    │            │
│           │                           │            │
│     有工具调用?                        │            │
│     ├── 是 → 执行工具 → 结果回灌 ──────┘            │
│     └── 否 → 跳出循环 ↓                             │
└──────────────────┬───────────────────────────────┘

┌──────────────────────────────────────────────────┐
│  Phase 3 · 回复保证(护栏)                         │
│                                                    │
│  模型调了工具,但没产出文字?                         │
│  → 强制再调一次(不带工具),逼它总结输出             │
└──────────────────┬───────────────────────────────┘

              输出回复给用户

你注意到了吗?Phase 2 这个循环里,没有任何 if-else 判断"该走哪条路"。模型自己在循环里决定:要不要调工具、调哪个、什么时候停。它说"我做完了"(不再请求工具调用),循环就自然结束。

我要做的事情只有两件:给它工具(Phase 2 循环里那些 tools),给它护栏(Phase 3 的回复保证)。我不编排它的流程,我只设计它手里的工具和它身后的护栏。 这就是阶 4 的样子——你从"编排流程的人"变成了"设计工具和护栏的人"。

一个重要的提醒:四阶不是线性的

画成一条直线是为了好讲,但真实的认知过程不是线性的。

我自己就是反复跳着走的。我在阶 1 调 prompt 调到怀疑人生(第 1 章),然后跳到阶 4 去重构循环(第 5 章),重构过程中发现工具设计有问题又跳回阶 3(第 4 章),改工具的时候发现上下文管理不对又跳到阶 2。真实的学习路径是螺旋的,不是阶梯的。

所以不用纠结"我现在在第几阶"或者"我什么时候能升到下一阶"。四阶的价值在于给你一张地图——当你卡住的时候,知道还有哪些方向可以看。你本来只盯着 prompt,现在你知道还有 context、harness、loop 三个方向可以排查。

这一章的工具:你在哪一阶?

下面这个自检不是考试,是帮你定位自己当前的"关注盲区"。大多数人会发现自己某一两阶特别强,另外一两阶几乎没关注过——那些没关注的,往往就是你 Agent 项目里隐藏问题的来源。

🔧 认知阶位自检

诚实回答以下问题,看看你的关注范围覆盖了哪几阶:

阶 1 Prompt

  • [ ] 你会不会在 system prompt 里加示例来控制输出格式?
  • [ ] 你能不能区分"必须遵守的规则"和"参考信息",并组织好它们的顺序?

阶 2 Context

  • [ ] 你有没有主动管理过模型的"视野"?比如哪些历史对话保留、哪些丢弃?
  • [ ] 当 Agent "健忘"的时候,你会不会去查"它那个瞬间到底能看到什么",而不是只知道改 prompt?

阶 3 Harness

  • [ ] 你写工具描述的时候,是当成 API 文档写,还是当成 prompt 写?
  • [ ] 工具失败时,返回的错误信息里有没有"下一步建议"?

阶 4 Loop

  • [ ] 你的 Agent 执行循环,能用一句话描述吗?如果描述不出来,是不是太复杂了?
  • [ ] 你有没有在代码里用 if-else 替模型做了它本该自己做的决定?

怎么读这个自检的结果

  • 如果某一阶你几乎全勾不了,那这一阶大概率是你当前 Agent 项目的瓶颈所在
  • 阶 1 和阶 2 是基础,阶 3 和阶 4 是进阶——但"进阶"不代表可以不管基础
  • 最危险的情况是:只关注阶 1,对 2/3/4 完全没意识。这意味着你看不到 prompt 之外的问题

小结

四阶认知说到底就一句话:做 Agent 不等于调 prompt。

Prompt 是起点,但只是起点。从 prompt 往外走,有 context(给模型什么信息)、有 harness(模型怎么跟系统交互)、有 loop(循环怎么设计)。每一阶都是你能动手优化的地方,而且越往外越是 Agent 工程的真正核心。

传统程序员有一个隐藏优势:阶 3 和阶 4 涉及的系统设计,正是你们的主场。所以不用被"AI 工程"这个词吓到——它在很多方面,其实就是你熟悉的软件工程,换了一批新的约束条件而已。

从下一章开始,我们进入这份手记的第二部分——具体怎么把一个 Agent 做出来。第 3 章先讲一个最基础但最容易被忽视的东西:颗粒度。

下一章

第 3 章 · 颗粒度与验证 —— 为什么大多数 Agent 项目会失控,以及怎么不让它失控。