1. 为什么“精通”一个AI编程助手,重点根本不在提示词
很多人第一次接触 Claude Code 这类终端里的 AI 编程助手,脑子里蹦出来的第一个念头是“我得去背一套万能提示词模板”。我一开始也这么想,甚至专门建了个文档收集各种“神级 prompt”。结果用了两周就发现,真正决定效率高低的,根本不是你怎么跟它说话,而是你怎么给它搭环境、划边界、控节奏。
这个判断听起来有点反直觉,但只要你真正在项目里跑过几轮就会明白:Claude Code 和网页版对话式 AI 最大的区别,是它能直接读写你的文件系统、执行命令、跑测试、看报错、再改代码。它不是一个“问答机器人”,而是一个能动手的协作方。你跟一个能动手的人合作,光靠嘴甜没用,得把工作台收拾干净、把规矩讲清楚、把验收标准定死。
所以这篇内容我想聊的,是一个开发者在真实项目里把 Claude Code 用顺手之后,沉淀下来的那套“工程化用法”。它适合已经装好工具、跑通过一两个小 Demo、但总觉得“好像没发挥出全部实力”的人。如果你还在纠结要不要用,那这篇可能偏深了;但如果你已经决定把它纳入日常开发流,下面这些经验应该能帮你少走不少弯路。
我把它拆成几个层面:先讲清楚它在终端里到底是怎么“思考”和“动手”的,再讲项目上下文怎么喂、权限怎么管、任务怎么拆,最后讲几个我踩过的坑和对应的绕行方案。全程不聊玄学提示词,只聊能复现的工程动作。
2. Claude Code 在终端里的工作循环:它到底在“看”什么
2.1 一次典型交互背后的完整链路
要把它用明白,得先知道它每次响应之前发生了什么。我用一个真实场景来还原:你让它“把用户模块的登录接口加上参数校验”。
它做的第一件事不是写代码,而是收集上下文。它会去读你当前工作目录下的文件结构,找到跟“用户模块”“登录接口”相关的文件,可能是routes/user.js、controllers/auth.js、validators/目录。这个过程它不一定一次读全,而是边读边判断“这个文件跟任务相关吗”。
第二件事是规划动作。它会形成一个内部的任务列表:先看现有校验逻辑长什么样,再决定是复用已有工具函数还是新写一个,然后才动手改。这个规划过程你在终端里能看到它一步步输出,但很多人会忽略——其实这个输出就是它给你的“施工方案预览”。
第三件事是执行与验证。它改完文件后,如果项目里有测试命令,它会主动去跑;跑挂了它会看报错再改。这个“改-跑-看-再改”的循环,是它区别于普通代码补全工具的核心。
理解这条链路之后,你就能明白为什么有些任务它做得又快又准,有些却反复绕圈:上下文给得对不对,直接决定它规划得准不准。你如果在一个几千文件的巨型仓库根目录直接下命令,它光找相关文件就要耗掉大量轮次,还容易找错。
2.2 上下文窗口不是越大越好,而是要“精准投喂”
这里有个常见误区:以为把整个项目都塞给它就万事大吉。实际上上下文窗口是有限资源,塞得越杂,它抓重点的能力越弱。我的做法是按任务粒度控制工作目录。
比如我要改支付模块,我不会在仓库根目录启动,而是先cd到支付相关的子目录,或者用它的文件引用语法明确告诉它“只看这几个文件”。这样它收集上下文的轮次少了,规划质量反而更高。
还有一个技巧是用项目里的“活文档”当锚点。我在每个模块目录下放一个简短的MODULE_NOTES.md,写清楚这个模块的职责、关键文件、对外接口。Claude Code 读到这个文件后,对模块的理解会准很多,不需要它自己去猜。这个习惯看起来是给它准备的,其实对新人接手项目同样有用,一举两得。
2.3 它“看不见”的东西,才是你真正要补的
Claude Code 再强,也有它天然看不见的东西:数据库里的真实数据分布、线上环境的配置差异、团队口头约定的潜规则、某个历史遗留字段为什么不能动。这些信息不在代码里,它无从得知。
我的应对方式是在任务描述里主动补背景。比如不说“优化这个查询”,而说“这个查询在订单量超过十万后变慢,目前走的是全表扫描,业务上允许加索引但该表写入频繁”。后面这半句业务约束,就是它自己绝对推不出来的。
提示:每次下任务前问自己一句——“这个决定背后有没有代码里看不出来的约束?”有的话,先写进任务描述里。
3. 把项目上下文喂对:目录结构、约定文件与任务边界
3.1 目录结构本身就是一种“提示”
一个组织良好的目录结构,对 Claude Code 来说就是一份免费的导航图。我观察到一个规律:它找文件的准确率,和目录命名的语义清晰度强相关。
举个对比。方案 A 的目录是src/a/、src/b/、src/utils/,方案 B 是src/auth/、src/order/、src/shared/。同样一句“给登录加校验”,在方案 B 里它几乎能直奔auth目录,在方案 A 里它得先读一堆文件才能判断a和b哪个是认证模块。
所以如果你打算长期用它,花半天时间把目录命名理顺,回报率极高。这不是为了它,是为了整个团队的可维护性,只是它把这个收益放大了。
3.2 约定文件:给 AI 也给人的“项目说明书”
除了前面提到的模块说明,我还会在仓库根目录放一个CONVENTIONS.md,写清楚代码风格、提交规范、测试命令、禁止事项。Claude Code 在动手前会参考这类文件,改出来的代码风格会明显更贴近项目现状。
这里有个细节值得说:约定要写成“可执行”的,而不是“口号式”的。比如不要写“保持代码整洁”,而要写“所有异步函数必须用 try/catch 包裹,错误统一走 logger.error”。前者它没法执行,后者它能直接照做。
我整理了一份自己常用的约定文件骨架,供参考:
| 条目 | 写法示例 | 为什么这样写 |
|---|---|---|
| 测试命令 | npm run test:unit | 它需要知道跑哪个命令验证 |
| 代码风格 | 使用 2 空格缩进,字符串用单引号 | 避免它按默认风格改乱 |
| 禁止操作 | 不要修改migrations/下已有文件 | 防止它“顺手优化”闯祸 |
| 错误处理 | 统一抛AppError,不直接throw new Error | 保证它改完风格一致 |
3.3 任务边界:一次只让它干一件事
我踩过最大的坑,就是一次性给它一个模糊的大任务,比如“重构用户模块”。结果它改了一大片文件,方向还跟我想的不一样,回滚都费劲。
后来我改成小步快跑:把“重构用户模块”拆成“把用户查询逻辑抽到 repository 层”“把校验逻辑统一到 validator”“给这三个接口补单测”。每个任务单独下,做完一个我 review 一个,确认没问题再下一个。
这样做的好处不只是可控。每个小任务完成后,它对这个模块的理解会累积在上下文里,下一个任务它做得更准。相当于你在带一个新人,先让他做小活建立默契,再逐步放权。
4. 权限与安全:让 AI 动手,但别让它“乱动”
4.1 默认权限模式下的“确认疲劳”怎么破
Claude Code 默认会在执行有副作用的操作前问你,比如写文件、跑命令。这个设计是对的,但用久了会出现“确认疲劳”——你开始无脑点同意,反而更危险。
我的做法是分级授权。读操作、跑测试这类无副作用的,我倾向于放行;写文件、删文件、执行数据库命令这类,保持确认。具体怎么配,取决于你用的版本和配置方式,核心原则是:破坏性越强,越要人工过目。
这里有个经验:别在赶时间的时候放宽权限。我见过有人为了快速跑通一个脚本,临时开了全自动,结果它把一个配置文件覆盖了。赶时间的时候人判断力最差,恰恰是最该保持确认的时候。
4.2 用版本控制当“安全网”
不管权限怎么设,我都会确保动手前工作区是干净的,也就是git status没有未提交的改动。这样万一它改歪了,一条git checkout .就能回到原点。
更进一步,我会在让它做较大改动前先提交一次,哪怕提交信息写“wip”。这样回滚点更清晰,也能用git diff精确看它到底改了什么。这个习惯救过我好几次——有一次它“顺手”改了一个我没让它碰的工具函数,diff 里一眼就看出来了。
4.3 敏感信息永远不进上下文
这一点必须单独强调。不要把密钥、令牌、生产环境连接串放进任何它可能读到的文件里。它读文件是不分“这个能不能看”的,你放在项目里的东西它都可能读到,进而可能写进它的输出或日志。
我的做法是敏感配置一律走环境变量,本地用.env且确保在.gitignore里,同时约定文件里明确写“不要读取.env”。这不是不信任工具,而是任何能读文件系统的自动化工具都该遵守的基本纪律。
5. 任务拆解与验证:让每一轮改动都可回滚、可验证
5.1 把“大目标”翻译成“可验收的小任务”
前面提过小步快跑,这里展开讲怎么拆。我的拆解标准是:每个任务做完后,我能用一条命令或一个动作验证它对不对。
比如“给登录接口加参数校验”这个任务,验收标准就是“跑一下针对登录接口的单测,全绿”。如果项目里没有对应单测,那我会先让它“给登录接口补一个覆盖参数校验的单测”,再让它改逻辑。顺序反过来,先有测试再改代码,验证就有了抓手。
这个思路其实就是测试驱动开发的老套路,只不过执行者从人换成了 AI。它反而更适合这种模式,因为它跑测试不嫌烦,改完自动跑,跑挂了自动看报错。
5.2 验证不只看“跑没跑通”,还要看“改没改歪”
测试全绿不代表改得对。我 review 它的改动时,重点看三件事:
- 改动范围:有没有碰我没让它碰的文件?用
git diff --stat一眼能看出来。 - 风格一致性:新代码跟周围代码风格是否统一?不一致的地方往往是它“自作主张”的地方。
- 边界处理:异常分支、空值、并发这些它容易忽略的点,有没有覆盖。
有一次它给一个查询加了缓存,测试全过,但我 review 时发现它没处理缓存失效,数据更新后读到的是旧值。这种问题测试覆盖不到,只能靠人看。所以测试是底线,review 是必须,两者不能互相替代。
5.3 回滚策略要提前想好
我给自己定了个规矩:任何一次让它做的改动,我都要能在三十秒内回滚。实现方式就是前面说的,动手前提交、工作区干净、改动范围可控。
如果某个任务它反复做不对,我的处理不是继续跟它磨,而是回滚到干净状态,重新组织任务描述。因为反复磨往往说明任务描述本身有问题,或者上下文给得不对,继续磨只是浪费轮次。回滚重来,换个说法,通常一次就过。
6. 几个真实踩坑与绕行方案
6.1 坑一:它在错误的目录里“找家”
有一次我在一个 monorepo 根目录启动,让它改某个子包的配置。它读了半天,最后改了一个同名但不同包的文件。原因很简单:根目录下有两个包都有config.js,它没分清。
绕行方案:先cd到目标子包再启动,或者在任务里明确写全路径。现在我养成习惯,动手前先确认工作目录,这一步花五秒,省下的是半小时的排查。
6.2 坑二:它“顺手”重构了不该动的东西
前面提过一次,它改了一个我没让它碰的工具函数。后来我分析,是因为那个函数跟目标任务在同一个文件里,它读文件时“觉得”这个函数写得不好,就顺手优化了。
绕行方案:在约定文件里明确写“只改与任务直接相关的代码,不要顺手重构”。同时 review 时重点看 diff 范围。这个坑的本质是它太“主动”,而主动性在协作里需要被约束。
6.3 坑三:长任务里它“忘了”前面的约定
任务一长,轮次一多,它可能会忘记你最开始说的约束。比如你开头说“不要改数据库 schema”,改到第十轮它可能就动了。
绕行方案:把关键约束写进约定文件,而不是只放在对话里。文件是持久的,对话是易失的。另外,长任务拆短,本身也能缓解这个问题。
6.4 坑四:报错信息它“看不懂”是因为你没给全
有时候它改完跑测试挂了,看报错却改不对。排查下来往往是报错信息被截断了,或者它只看到了最后一行。这时候我会手动把完整报错贴给它,并指出关键行。它拿到完整信息后,通常一次就能改对。
这个坑提醒我:它再智能,输入不完整它也巧妇难为无米之炊。该补的信息要补,别指望它猜。
7. 把它变成日常习惯之后,我的工作流长什么样
用到现在,我的日常流程大概是这样:早上到工位,先git pull保证工作区干净;要改哪个模块,先cd过去;动手前扫一眼约定文件还在不在;下任务时把业务约束写清楚;它改完我先看git diff --stat再跑测试;确认没问题就提交,有问题就回滚重来。
这套流程听起来琐碎,但跑顺之后几乎不占额外时间,反而因为返工少了,整体快很多。我最大的体会是:别把它当“许愿机”,把它当一个需要清晰指令、需要验收、需要边界的协作方。你对它越像对同事,它表现越像同事。
最后分享一个小技巧:我会定期回顾那些它做得特别好的任务,把当时的任务描述存下来当模板。下次遇到类似任务,改几个关键词就能复用。这比收集“万能提示词”实在得多,因为它是从你自己项目里长出来的,贴合你的上下文。
这个方向后续还能继续挖,比如怎么让它参与 code review、怎么跟 CI 流程结合。但那是另一个话题了,先把上面这些基础动作跑顺,收益就已经很明显。