1. 无状态模型的失效:AI 协作中最容易被忽视的上下文断层
1.1 一次典型的「AI 失忆」现场
先说个我最近的真实经历。某天上午,我对着一个后端项目连续调了三个小时的接口逻辑,AI 编码助手全程在线,从路由设计、鉴权中间件到数据库表结构,聊得清清楚楚。中途我重构了一个核心模块的目录结构,把services/order.go挪到了billing/order/service.go,顺带改了包名。下午我重新打开一个新的对话窗口,想让它帮我在订单模块里补一个批量导出接口。
结果它张口就问:「请提供订单模块的相关代码」,还建议我在services/下新建文件。那一刻我就知道,上午那几个小时的上下文,在它重新启动的那一刻,就已经归零了。
这个场景几乎所有深度用过 AI 编码工具的人都不陌生。你给它分析了半天项目,它似乎心领神会;但只要换一个会话、换一台机器,或者隔了一晚上,它就像失忆了一样,把你所有口头的约定、架构决策、编码习惯全忘得干干净净。很多人把这个归咎于「AI 还不够聪明」,但我更倾向于换一个角度来看:这是我们自己还没有建立一套「记忆工程」体系导致的。
无状态模型本身不是缺陷,它就是大语言模型的工作方式——每次调用都是一次独立的推理,过去的信息只存在于对话上下文里。可问题是,软件开发恰恰是一个强状态、强长期上下文的领域:项目有历史包袱,有架构决策记录,有团队约定的代码风格,这些都不是靠一轮对话能完整传递的。
1.2 Token 窗口很大,但「记忆感」依然很浅
有人可能会反驳:现在的 AI 编码助手动辄支持几十万、甚至上百万 token 的上下文窗口,你把整个项目塞进去不就行了?
我试过,效果差强人意。首先,把整个代码库塞进上下文是不现实的,大部分商业工具也有配额和性能限制,检索和分析的延迟会明显上升。其次,也是更本质的问题:token 窗口再大,也只是一个短期缓冲区,而不是长期记忆。它像一块白板,每次会话开始时都是干净的,你可以往上写很多内容,但下次会话开始时它又是空白的。哪怕窗口足够大,AI 在窗口里「看到」的东西也未必是它该优先关注的——项目里最有价值的架构约束、踩坑记录、命名惯例,往往淹没在大量无关的样板代码里。
打个生活化的比方:你请了一位临时助理来帮你处理一天的工作,他记性极好,当天交代的事一件不忘。但第二天换一位新助理来,他连你公司的组织架构都不知道,也不清楚你讨厌什么样的汇报格式。每次都要重新交代一遍,哪怕你的旧助理昨天已经整理好了员工手册——但新助理没有读过它。
所以真正的问题不是「窗口不够大」,而是我们没有把项目的关键记忆沉淀成一个可被 AI 主动读取的载体。如果有一份文件,每次 AI 启动新的工作上下文时都会自动加载,里面清晰地写着这个项目的架构约定、命令规范、代码风格、需要规避的坑,那「失忆」问题就能从根上缓解大半。
1.3 范式转换:从「每次口述」到「声明式配置」
早期大家是怎么应对 AI 失忆的?主流做法是攒一个超长私有提示词,每次开新会话时手动粘贴进去,甚至用各种方式把提示词做成系统级模板。我见过有的开发者把提示词写到几千字,里面涵盖了项目概况、角色设定、输出要求、禁止事项,写得比项目文档还复杂。
这种做法在单机小项目上勉强能跑,问题在于它完全依赖「人肉传输」。提示词存在个人笔记里、存聊天记录里,团队成员之间各存一份,版本稍微一变化,几条上的约定就开始分裂。更麻烦的是,这些提示词描述的东西往往已经从项目实际中漂移了——项目重构了三次,提示词还停在最初的架构描述上。
而从无状态模型到声明式配置,解决的是两个层面的问题:让记忆成为项目的一部分,而不是对话的一部分。第一,记忆文件放在仓库里,进入项目的任何人都能读取和维护,它跟代码一起走,不依赖某个人的个人提示词;第二,AI 编码工具在启动时会主动加载这些文件,不需要开发者每次手动拼接上下文。这就是标题里说的「范式转换」——把零散的对话约定,转变成结构化的、可版本化的、随仓库分发的声明式配置。
市面上已经开始出现类似的记忆文件约定,比如有的工具约定某个命名规则的 Markdown 文件,AGENTS.md、项目目录下的规则文件等等,大家的目的都一样:给 AI 一个有据可循的稳定记忆源。
2. Memory 工程的核心逻辑:记忆不能只靠对话
2.1 记忆的分层逻辑
在深入 AGENTS.md 之前,我觉得有必要先把「记忆」这件事拆开看。工程里的记忆至少可以分三层:
| 记忆层级 | 生命周期 | 载体 | 例子 |
|---|---|---|---|
| 对话内记忆 | 单次会话 | 上下文窗口 | 你刚才让它改了什么函数 |
| 项目记忆 | 项目生命周期 | 仓库内文件 | 构建命令、架构约束、代码规范 |
| 团队记忆 | 团队长期积累 | 共享文档/模板 | 团队对错误处理方式的共识 |
无状态模型天然只支持第一层。我们做 Memory 工程,要解决的就是把第二层、第三层的内容,稳定地搬进 AI 的上下文窗口中。
注意这里有个关键点:不是把整个项目历史都喂给 AI,那太离谱了。我们要做的是把项目的「关键约束」提炼成契约式的文本,让 AI 每次开始工作时,能通过一个低成本的方式读到这份契约,而不是靠你重复复述。
2.2 从「大提示词」到「项目记忆文件」的路径
我最早维护的那套私有提示词,后来经历了三个阶段的演变。
第一阶段是纯口头约定。AI 用久了,我发现它总是把错误处理写成fmt.Println加return,而项目里要求的是统一错误包装。我每次都要在新会话里提醒一次,烦不胜烦。
第二阶段是笨拙的大提示词。我把所有约定集中到一份巨大的个人提示词里,每次开新会话都粘贴,效果确实有,但问题也随之而来:提示词里提到的目录已经不存在了、链接的规范文档已经超时了,AI 照着过期的约定干活,反而添乱。
第三阶段才是真正的转折点:我学着把记忆文件放进了项目仓库。仓库根目录多了一个大家都默认会读取的说明文件,里面只写了三部分内容——项目怎么跑、代码规范是什么、有什么绝对不要做。AI 工具在项目目录下启动时,绝大多数都会自动读取这份文件作为初始上下文。从那一刻起,我对 AI 的「概率性失忆」基本告别了。
这个路径本身很有代表性:记忆必须实体化,必须从大脑中搬到文件系统中,才能被 AI 稳定访问。
2.3 声明式配置,为什么优于程序化指令
这里再说一个容易被忽视的理念问题:我们到底应该怎么给 AI 写规则?
在初期,很多人习惯用命令式语气写约束,比如「你必须先执行测试,再执行构建」「遇到 X 问题时,你必须先执行 A,然后执行 B」。这种写法不是不行,但维护成本非常高——一旦流程变化,整段重写,指令之间还容易互相冲突。
声明式配置的思路不同:你不告诉 AI 具体怎么一步步做,你告诉它这个项目的状态和约束是什么。比如「测试命令为make test」「所有公共方法必须有注释」「禁止在服务层直接操作数据库」。剩下的是「怎么做、什么顺序做」,AI 自然会在符合约束的前提下自己规划。
用人话讲,命令式是请了个只会照章办事的员工,你离开就开始出问题;声明式是请了个靠谱的工程师,你告诉它边界和标准,剩下的它自己发挥。前者遇到稍微复杂的场景就会卡壳,后者在约束清晰的前提下,能灵活处理大量的意外情况。AGENTS.md 这种声明式配置之所以能成为趋势,核心就是因为它抓住了「约束比流程稳定」这个本质。
3. AGENTS.md 的设计与结构:一份能用的配置文件长什么样
3.1 先看一个最简可用版本
AGENTS.md 这个概念,本质上就是给 AI 代理阅读的项目说明书。它在仓库里的形态是一个 Markdown 文件,通常放在根目录,也可以按子目录拆分。
我拿一个真实的轻量项目举例,这份文件是精简过的:
# AGENTS.md ## 项目概述 这是一个内部工单管理系统,前端使用 React,后端使用 Go。 代码仓库采用 monorepo 结构,`web/` 和 `api/` 两个子目录分别管理前端与后端。 ## 技术栈与命令 - 后端服务:`cd api && make run` - 前端开发:`cd web && npm run dev` - 单元测试:`cd api && make test` - 接口文档:`api/docs/` 目录下,修改接口后必须同步更新 ## 编码规范 - Go 代码遵循官方标准,错误处理使用 `errors.Wrap` 包装并附加上下文。 - React 组件使用 TypeScript + Hooks,禁止使用类组件。 - 公共函数和导出组件必须写 JSDoc 注释。 - 数据库迁移脚本放在 `api/migrations/`,新脚本命名格式:`日期_描述.sql`。 ## 约束 - 不要在业务代码中直接使用 `log.Printf` 输出;统一使用 `pkg/logger`。 - 不要修改 `web/src/api` 下的自动生成文件,如有需要请先运行代码生成脚本再提交。 - 涉及环境变量时,一律通过配置文件读取,禁止硬编码。你没看错,就是这么朴素。这份文件没有角色扮演,没有夸张的设定,更像是一份高度浓缩的「新成员入职手册」,只不过读者不是人类,而是 AI。它涵盖了项目概况、技术栈、命令、代码风格、约束五个维度,约 20 多行。
关键在于:一旦把这个文件放到仓库根目录,AI 工具在项目里启动新会话时,就会自动把它作为初始上下文的一部分读取。你不需要在新会话里重复交代任何内容,它自己就知道这个项目用什么语言、跑什么命令、遵守什么规范。
3.2 每个核心字段的设计意图
项目概述:给 AI 一个全局视角。它不知道你在做电商还是做支付网关,一份两句话的概述能让后续所有决策都建立在正确的前提下。这里要注意,项目的业务定位一定要写清楚,否则 AI 容易在不同模块之间瞎猜。
技术栈与命令:这是 AGENTS.md 里性价比最高的一部分。因为 AI 最大的不确定性之一就是「这个项目怎么运行」。你直接告诉它命令,它就不用靠猜了。特别是测试命令,务必写上:AI 写完代码之后能自己验证对不对,这是质量下限的保证。
编码规范:不需要罗列一堆教科书级的规范,只写这个项目特有的、和通用做法不一样的地方。比如团队规定错误必须包装、某些目录不可动、格式工具用哪个,这些才是真正能减少返工的信息。
约束:我认为这是 AGENTS.md 的核心价值所在。把项目里最容易出问题的几个「红线」明确写出来,AI 在思考过程中会自动绕开这些坑。比如「自动生成文件不要手改」「环境变量不要硬编码」,这些一旦出事就是大返工,值得明确写进文件。
还有两类内容我建议不要写进去:一类是过于抽象的口号,比如「代码要优雅」「保证高质量」,AI 无法把这类话映射成具体行动;另一类是过于漫长的背景故事,比如项目的五年规划,这些信息对 AI 做一次代码修改毫无帮助,反而稀释了有效信号的密度。
3.3 多文件组织:从单文件到 AGENTS 目录
单文件适合中小项目,项目一旦复杂起来,把所有内容塞进一个 README 式的 AGENTS.md 就会变得臃肿。现在主流的做法是分成一个入口文件加若干子文件:入口 AGENTS.md 只保留最重要的三条约束和目录指引,细节放到对应的子文件里。
比如这样:
AGENTS.md # 主入口,只写核心约束 AGENTS/ api-usage.md # 接口调用与错误处理约定 coding-style.md # 语言级风格规范 workflows.md # 测试、构建、发布流程 architecture.md # 模块关系与依赖方向入口文件的最后,加一段指向子文件的说明,比如「关于接口错误处理的详细约定,见AGENTS/api-usage.md」。当 AI 在推理过程中遇到相关问题时,可以自己判断是否需要去读那个子文件。
这种多文件组织方式本质上是在给 AI 做一个分级加载的内存系统:核心信息永远保持轻量,细节按需加载,跟操作系统的两级缓存有点像。对于代码量很大的老项目,这个设计几乎是必需的,否则 AGENTS.md 本身就会变成一个 AI 读不完的巨大文本。
4. 实战落地:从零为真实项目编写 AGENTS.md
4.1 动笔之前,先做「项目体检」
很多人第一次写 AGENTS.md 时容易犯的毛病,就是凭空对着一个空白文档憋内容。这完全没有必要,因为你项目里已经有大量的信息源等着你去提取,只是它们现在是散落在人脑里的。
我的建议是,打开项目之前,先回答下面这些实际问题:
- 从克隆仓库到本地跑起来,需要哪几条命令?有没有需要手动配置的环境变量或服务?
- 项目的测试体系是什么?单元测试、集成测试分别用什么命令跑?
- 代码风格上有哪些和主流规范不一致的约定?比如团队坚持用
snake_case还是camelCase,缩进用制表符还是空格? - 哪些目录是不能手动修改的?哪些文件是自动生成的?
- 新增一个功能模块时,需要同步更新哪些文件?比如路由注册、数据库迁移、接口文档。
- 之前的开发中有没有反复踩过的坑?比如某个库的已知限制、某个部署环境的特殊要求。
拿这些问题的答案去写,AGENTS.md 才会真正有信息量,而不是一堆废话。我特别推荐把「跑起来需要哪些命令」和「测试怎么跑」这两个问题放在最前面,因为这两条是 AI 保证输出质量的基础设施。
4.2 第一版写完之后,怎么验证它真的有用?
写完 AGENTS.md 并不算结束,关键要验证它真的被 AI 读进去了。我一般用三步验证法:
第一步,在项目根目录开一个全新的 AI 会话,故意不粘贴任何额外背景,直接问它:「这个项目的技术栈和启动命令是什么?」如果它能准确回答,说明 AGENTS.md 被加载了。如果答非所问,你先检查文件位置对不对,是不是放在了根目录、文件名是否准确。
第二步,让它执行一个带约束的任务,比如「在services层新增一个方法,处理超时订单的状态更新」。然后看它输出的代码是否符合 AGENTS.md 里的约定:错误是用自定义的包装器处理的吗?测试文件有没有同步生成?有没有在业务层碰数据库?
第三步,也是最有意思的一步:故意提出一个违反约束的请求,比如「帮我在服务层直接写一个查询数据库的函数」。观察 AI 的反应。合格的 AGENTS.md 应该让 AI 在这种时候主动提醒你「这个操作不符合项目约束,建议放到数据访问层」,并给出替代方案。如果没有这个反应,说明约束写得还是太弱,语义不够清晰,需要加强措辞。
4.3 把 AGENTS.md 和 CI 流程绑在一起
文件写在仓库里,如果不加任何保障,慢慢就会过期。我自己的做法是把它纳入代码评审流程:任何涉及项目结构、构建命令、代码规范变动的 PR,都要同步检查 AGENTS.md 是否需要更新。
更进一步的话,可以在 CI 里加一个小脚本,对 AGENTS.md 做格式校验,比如检查是否包含必填的标题(项目概述、命令、约束),检查目录引用的链接是否有效。不是每个团队都有余力做这一步,但只要加上了,就能最大程度避免「文档和代码分家」的老毛病。
我当时给团队加了一个很简单的检查,只有 30 行 Python,把 AGENTS.md 中引用的本地文件路径都提取出来,逐个检查是否存在。效果立竿见影:从那以后,AGENTS.md 里指向子文件的链接再也没断过。
5. 我踩过的那些坑:AGENTS.md 的反模式清单
5.1 把 AGENTS.md 写成了 README 的复制品
这是最常见的坑。我见过不少人把 AGENTS.md 写得像项目简介:一上来就是「本系统旨在为用户提供高效便捷的……」然后真正做到项目运行说明、编码规范的部分,反而一笔带过。AI 每次启动时都要先读一大段没有操作价值的信息,真正重要的约束沉在最下面,甚至根本没写到。
我后来给自己定了一个规矩:AGENTS.md 里的每一句话,都必须能直接映射成 AI 的一个行为约束或决策依据。凡是「我们很重视」「系统很强大」这类描述性内容,一律删掉。写完后我会通读一遍,如果某段话 AI 读完之后没有任何可操作的行为变化,就说明它在浪费 token。
5.2 禁止事项写得太多、太零散
有些团队喜欢在 AGENTS.md 里列一大堆「不要做 X」「不要做 Y」,结果 AI 反而不知道哪些是真正重要的。这里需要一个优先级意识:约束写十条,AI 每条都会读,但它不会每条都同等重视。
我的经验是,禁止事项超过五条就会开始失效。你应该把前三条留给真正会导致严重返工的红线——比如「不要手改迁移脚本」「不要在业务层写裸 SQL」「不要滥用全局变量」——后面的内容要么合并,要么降级到子文件里。约束要有层次,主文件管红线,子文件管细节。
5.3 规则太死,把 AI 的能力锁死了
还有一类反模式,是把 AGENTS.md 写成了严格的流程手册:第一步必须这样,第二步必须那样,输出必须用什么格式。这种写法短期看似乎约束住了 AI,但长期看会让它的表现变得极其僵硬,遇到流程没有覆盖到的情况时,反而不知道怎么办。
声明式配置的精神是「守住边界,放开过程」。你要描述的是「满足什么条件」「遵守什么约束」,而不是「每一步的精确顺序」。比如「提交信息必须包含对应的 issue 编号」是约束,而「提交之前必须先 git pull 再 commit」就太死板了,遇到冲突时 AI 反而会卡住。
5.4 忘了 AGENTS.md 需要持续维护
这个问题最隐蔽,也最致命。项目重构了、目录改了、包名换了,AGENTS.md 还停在三个月前。AI 每次加载它,读到的是过期的项目结构,然后按照错误的信息做出更错误的决策。这时候 AGENTS.md 不但没有帮上忙,反而成了给 AI 喂错误信息的来源。
解决方案其实也简单:把它当成一个活文档,每次大重构之后强制自己更新。把「更新 AGENTS.md」写进团队的 PR 模板里,或者像我前面说的,在 CI 里做基本的完整性检查。宁可让它短小、准确,也不要让它冗长、过期。
6. 从个人技巧到团队基建:Memory 工程的下一步
6.1 让「记忆」成为团队共识的载体
AGENTS.md 最大的价值不只在于帮个人应对 AI 失忆,更在于它天然是一个团队级别的协作契约。因为文件跟着仓库走,团队里的任何一个人对 AI 的行为约定作出修改,全组都会同步生效。这比每个人维护一份私有提示词要健康得多——规则不再散落在个人笔记里,而是沉淀在公共代码库中。
我现在的习惯是,在项目设计评审时就把 AGENTS.md 的更新作为一项常规交付物。架构评审通过后,顺手把新的架构决策写成两句话加进 AGENTS.md,这样后续所有人在这个仓库里调 AI 时,都能站在同一个认知水平线上。它其实就是团队知识库的一个轻量级、机器可读的入口。
6.2 静态配置之后,动态上下文是更大的机会
AGENTS.md 的文件形式大概率还会继续演进,但更值得关注的是它背后的设计理念——按需加载、分级记忆、动态组装。
现在已经有一些工具在做智能上下文管理:根据当前正在编辑的文件,自动把项目里相关的架构说明、依赖关系、相似代码片段注入上下文。这种能力如果再往上走,AGENTS.md 这种静态配置文件就会升级成一个「索引」,AI 根据当前任务动态决定去加载哪部分记忆。
我有预感,未来两年会看到越来越多的项目在代码库里沉淀这种结构化的 AI 记忆来源,AI 编码协作的质量,将从「模型能力竞争」逐步转向「上下文工程质量竞争」。哪个项目能把记忆组织得又准又轻,哪个项目的 AI 产出质量就会明显高一大截。
6.3 对开发者来说,这意味着什么?
说得直白一点,进化了:以前写代码是跟编译器打交道,未来的写代码工作会越来越多地变成跟 AI 描述清楚你要什么,而描述清楚的前提,是你先把项目本身的记忆体系搭建好。这不是一门可以投机取巧的技能,它需要你在实际项目里不断打磨:什么样的约束写得有效,什么样的内容写进去是噪音,每个项目都有不同的答案。
就我个人而言,自从把 AGENTS.md 这类记忆文件作为项目标配之后,AI 编码的体验发生了实质性的变化。最明显的一点是,我不再需要反复向它解释项目背景了,它自己对项目的理解稳定地保持在一个较高水位上。过去那种「上午聊得好好的,下午全忘了」的挫败感,已经很久没有出现过了。
如果你还在被 AI 编码助手的「失忆」问题困扰,我的建议很简单:别想着继续堆更长的提示词,试着打开项目根目录,写一份干净的 AGENTS.md,把项目怎么跑、约束是什么、红线在哪里写清楚。从明天的新会话开始,你会明显感受到不同的。