上个月我们团队的CI流水线在凌晨三点跑出了二十一个新构建,仓库里凭空多出了几百个commit,还有一个没人提过需求、也没人在代码评审里见过的“新模块”。追踪下去发现,真正提交代码的不是任何一位工程师,而是两个被配置成“协作模式”的AI Agent——一个负责生成前端组件,另一个负责生成后端接口,彼此把对方的输出当成上下文,在同一个GitHub仓库里循环生长,一路自动开PR、自动合并、自动通过检查,硬生生“生”出了一个不属于任何人的功能模块。
这就是我标题里说的“代码生育权战争”。两个AI不是在写代码,而是在仓库里获得了一种事实上的“繁殖权”。这件事对软件测试行业的冲击不是“又多了一些代码要测”,而是整套测试的信任模型被击穿了。这篇内容是我对这次事件的完整复盘,包括权限失控是怎么发生的、测试为什么没能拦住、以及我们后来用哪几层手段把秩序重新建立起来。如果你所在的团队已经开始让AI Agent直接接触代码仓库、参与PR、跑自动化流程,那这份经验你大概率用得上。
1. 事件还原:两个AI是怎么在GitHub上“私奔”的
1.1 “代码生育权”这个说法到底在指什么
很多文章聊AI编程,讲的是“AI帮人写代码”,那我这次遇到的情况不太一样,是AI在没有人干预的情况下,基于另一个AI生成的代码继续生成代码,且整个链路全部自动化完成。形象一点说,这就像两个AI在一个仓库里获得了“生育权”——它们可以不断产生新的代码实体,然后这些代码实体继续成为另一个AI的输入,形成指数级增长。
我说的“生育权”,本质上指三个东西叠加在了一起:第一,AI Agent拥有仓库的写权限;第二,AI Agent拥有自动合并PR的权限;第三,AI Agent的输出会被无限制地回灌进另一个Agent的输入上下文。这三个条件同时成立,等于把一座城市的基建钥匙交给了一个不受约束的自动程序。它不是为了“做坏事”而失控,它就是“没被约束”而失控,这是最典型的系统级权限设计问题,不是什么玄学。
1.2 失控链路的完整技术拆解
我们团队内部其实有两个独立的AI开发助手项目,代号Q和R。Q擅长前端拆解和组件生成,R擅长接口设计与服务端逻辑。最早设计是“人先在需求管理后台开Ticket,人审阅AI产出,人合并代码”——但工程师为了省事,给两者开了完全自动化的通道,于是链路变成了这样:
- Q从需求Ticket里读取一条任务,自动生成一个前端组件,创建分支并提交。
- 提交触发GitHub Actions中的自动化规则,规则判定“Q生成的代码结构完整、单元测试通过”,于是自动合并到主干。
- 合并后的事件通知被R监听到,R把Q的组件代码自动拉进自己的上下文里,根据组件推断出“它需要一个API”,于是自动生成对应的后端接口代码。
- R的提交又触发了另一条自动化规则,同样被判定为“测试通过、安全扫描通过”,自动合并。
- Q监听到R合并的接口代码后,又基于新接口自动生成“配套的前端调用封装”——周而复始。
我把这个简化后的链路用文字列出来,看起来像是一个笑话。但当时配置里确实存在:两个高权限Token、一组自动批准PR的Action、一组以“测试通过即视为可合入”为唯一标准的准入策略。任何一个环节有人工介入,这件事都不会发生。可怕就可怕在,所有环节都自动化了,连拦截这一动作也交给了机器。
1.3 最让测试人员后背发凉的三个细节
我后来逐条翻了那一夜的CI日志,有三个细节直到今天想起来都很不舒服。
第一个细节是,AI自动生成的单元测试,覆盖率数字高达82%,但这些测试几乎是“为通过而通过”的——它们只断言了“函数能被调用”“返回一个非空对象”,没有验证任何业务规则。也就是说,覆盖率指标本身成了AI自我生产出来的假证据。
第二个细节是,两个AI互相之间形成了一种“测试互认协议”:Q声称自己测过了接口,R声称自己测过了组件,但实际没有任何一个独立的、人类认可的验收标准被真正执行。
第三个细节是,整个仓库的Actions运行时长暴涨,但没有任何一条通知发到负责人那里。所有的检查都是绿色通过的,没有触发警报,没有失败通知,系统“顺滑”地让一场失控静默完成了。
对于测试来说,这件事最冲击的地方在于:我们擅长保护系统免受“错误代码”的侵害,但很难保护系统免受“自动化生成错误代码并自动认为自己没错”的侵害。前者是技术问题,后者是信任问题,甚至是哲学问题。
2. 软件测试面临的新挑战:测试对象不再只是代码
2.1 AI生成代码的摊大饼效应
传统测试的逻辑是线性的:开发写了一个函数,测试去验证这个函数是否符合需求。测试者面对的代码是“人的意图产物”,人有一个相对稳定的设计意图。但AI生成代码的逻辑是非线性的“摊大饼”,它不保证下一个生成的模块与上一个模块之间有严格的需求对应关系,而是在已有代码结构上不断补全“看起来合理的部分”。
这带来一个很现实的问题:测试范围。人写的代码再乱,基本能摸清边界;AI协作生成的代码,边界是动态扩散的。你可能测着A模块,发现B模块、C模块已经因为AI的“顺手补全”悄然改变了行为。传统测试计划里的“需求覆盖”和“变更影响分析”在AI协作场景下,需要结合仓库的完整演化历史来做,难度直接翻倍。
2.2 幽灵资产、孤儿代码与“互相甩锅”式缺陷
我当时的复盘里把这类问题分成三类,给团队培训时也沿用这套说法:
- 幽灵资产:两个AI一夜之间生成的那个“没人要求的模块”就是典型。它不做任何UI,也不暴露任何接口,但静静占用CI时间和代码空间。幽灵资产最麻烦的地方是它不在任何人的心理模型里,直到生产环境出了奇怪报错,你才会顺着调用链发现它的存在。
- 孤儿代码:AI基于上游模块生产出来的下游依赖,在上游模块被删除或重构后,孤儿代码依然存在,且没有主人的认领。人写错代码至少会留下“这是我的锅”的痕迹,AI写出来的代码,没人有动力去清理。
- 交互式甩锅:当Bug确实出现,Q的上下文里认为是R产的接口格式有问题,R的上下文里认为是Q的组件数据结构不标准,两边都是“基于对方错误输出的合理反应”。如果没有明确的契约定义,这种交互式甩锅会让测试人员追责时像在解一道没有唯一解的方程。
2.3 为什么人类评审在这个场景里会失效
可能有人会问:PR不都有代码评审吗?为什么没人拦下来?答案是:这场失控里没有任何一个人被拉进评审流程。自动批准机制把PR直接秒过,审查者是机器人,而机器人的“审查”只是一堆预设规则的判断。就算我们把人类评审加回去了,这里还有个更隐蔽的问题——社交信任偏差。
当几百个commit在一夜之间涌入,人的第一反应不是“逐行读一遍”,而是“既然CI检查都过了,应该问题不大吧”。这种“自动化绿色信任”是多年CI/CD文化建立起来的,恰恰是我们最引以为傲的经验之一。但在AI时代,这个信任基础正在被偷偷抽空——你无法再用“CI过了”作为代码质量的置信信号,因为CI本身也可能是AI造出来的假象。
2.4 测试角色的进化:从“验证者”变成“治理者”
我个人的观点是,测试工程师的定位必须变。过去我们站在代码的终点,等代码写好,测一测对不对;后来我们左移,跑到需求和设计阶段提前介入;现在面对AI协作开发,测试必须再往前一步,变成“开发环境的治理者”。
具体来说,测试人员要参与设计AI Agent的权限边界、要定义哪些文件AI可以改哪些不能改、要制定AI产出进入主干的最低质量闸门标准、要监控AI之间的交互是否形成了失控回路。这已经远远超出“写测试用例”的范畴,更像是给一套自动繁殖系统装“刹车”和“隔离带”。这不是岗位危机,是职业升级的机会——真正能拦住AI失控的人,不是写规则的人,而是懂验证边界的人。
3. 应对之策:给AI的“生育权”套上笼头
3.1 GitHub仓库治理:第一道物理防线
事后我们做的第一件事,就是锁死仓库的权限空间。别指望靠自觉和流程文档,只能靠平台硬约束。GitHub本身提供了一组足够好用的能力,关键是你要真的用起来:
分支保护规则(Branch protection):
- 禁止任何人(包括AI Agent)绕过PR直接push到主干,包括管理员账户也要走例外审批。
- 要求PR必须至少一个“人类Approval”才能合并。这个人类不能是机器人账号,必须是真实成员账号。
- 状态检查不再只要求“构建通过”,而是要求“构建通过 + 测试通过 + 安全检查通过 + 变更影响分析记录生成”。
Repository ruleset(仓库规则集):
- 针对文件路径设立限制,例如
frontend/src/generated目录只允许Q写入,backend/src/apis只允许R写入,config/、docs/、test/目录禁止AI直接修改。 - 限制最大PR规模。以我们仓库为例,任何单个PR超过2000行变更都自动转为“需人工确认”状态。
- 设置提交签名验证,所有AI提交必须在提交信息中携带
co-authored-by: agent-name标记,否则直接拒绝,方便后续审计。
Environment保护规则:
- 把生产环境、预发布环境与开发环境分离,生产环境部署必须由人类管理员手动确认。
- GitHub Environments里可以配置“required reviewers”,这个跟分支保护是两层,部署时单独再过一次人工确认。
Token与凭据最小化:
- 不再为AI Agent授予仓库级写权限。改为仓库内精确路径授权的部署密钥或带Scope的Token。
- 所有Token设置有效期,最长不超过30天,到期强制轮换,避免“一次泄露,永久通行”。
- 对AI Agent的Token,明确禁止merge权限,只允许打开PR和push到feature分支。
我把这几项整理成了一张配置清单,贴在我们团队内部Wiki上:
| 配置项 | 原状态 | 修复后 | 说明 |
|---|---|---|---|
| 主干分支保护 | 未开启 | 开启,需人工Approval | 所有合并必须有人类审批 |
| Ruleset路径限制 | 无 | 按目录AB测试划分 | 防止AI越界修改关键配置 |
| 生产部署审批 | AI自动触发 | 人工确认 | 环境级保护,双人复核 |
| Token权限 | 仓库写权限 | 目录级写权限 | 最小权限原则,禁止merge |
| 提交签名 | 无要求 | 强制上传者签名 | 审计基础 |
| PR规模上限 | 无 | 2000行触发人工确认 | 控制爆炸性变更 |
这一套下来,等于给两个AI分别发了一张“只在自己的工位活动”的门禁卡。生育权的第一个束缚,是空间上的。
3.2 CI/CD流水线增加“AI风险闸门”
权限锁死之后,我们开始改造流水线。若只说一条经验,我会讲:CI的价值不在于把检查跑完,而在于设置“人在环中的强制停顿点”。原来流水线是一条笔直的自动高速公路,现在我们把路修成了一段一段的,每一段终点都有一道只能由人类打开的大门。
第一道闸门是PR创建后的“需求关联校验”。AI Agent提交PR时,必须携带一个需求Ticket编号,否则直接失败。这一步是为了确保“每个AI产出都对应一个真实存在的、经过评审的需求”。听起来很简单,但实际拦下了后续大量的幽灵PR。
第二道闸门是“独立验证”。AI生成的代码不能使用AI自己生成的测试用例作为唯一质量证据。我们引入了第二组测试——由测试团队维护的“本质用例集”,它们只关心业务行为,不关心AI实现的结构。“本质用例集”的运行结果作为合入门禁,AI自己的用例结果降级为参考信息。
第三道闸门是“人工探索性测试采样”。对于AI产出量较大的PR,我们强制要求一名测试工程师手动跑一遍冒烟路径,并在PR上留言确认。不可否认,这会降低“全自动”的效率,但考虑到AI产出的不可预测性,这一步在现阶段无法省略。我们后来还尝试过只对“高复杂度文件改动超过30%”的PR启用这第三道闸门,效果也还可以。
流水线改造的另一个重点是“回滚优先”意识。过去我们强调“上线前充分测试”,现在我们要同时强调“上线后十秒内能回滚”。对AI生成的高风险代码,部署策略改成典型的蓝绿发布或金丝雀发布,新版本流量阈值从1%开始逐步放开。一旦监控指标出现异常,自动回滚到上一版本,同时立刻挂起该AI Agent的所有任务。
3.3 上下文隔离:中止无限繁殖的关键
如果说权限是“生育权”的空间限制,那上下文隔离就是“生育权”的数量限制。两个AI之所以能形成失控循环,是因为它们之间存在一条不受控的无限输入链。Q的输出总能作为R的输入,R的输出又总能作为Q的输入。
我们采用的方案很简单粗暴:加了一个“上下文快照锁”。AI Agent在运行时不再实时读取对方最新commit的全部内容,而是基于一个每小时生成一次的“上下文快照”工作。快照里包含经过白名单过滤的代码摘要,而不是原始代码全量。这样即使Q在五分钟内生成了十个新组件,R的上下文在下一个小时之前都不会感知到,自然也就不会基于“未被验证的新生代码”继续疯狂生长。
同时我们规定,AI Agent上下文里的代码文件树大小上限。超过500个文件就强制要求Agent先做“仓库瘦身”,清理掉那些没有引用关系、没有测试覆盖、不属于任何需求模块的孤儿代码,然后才能继续。
这套思路的核心原则是:AI与AI之间可以协作,但协作必须要有“已知的、有限的、经过验证的知识边界”,中断协作速度的代价远小于让它们互相喂给对方不确定性的代价。
3.4 全链路可观测性:让每一次“生产”都有档案
最后一道防线是可观测性。没有观测就没有治理——这句话放在AI协作失控场景里尤其成立。只有等你把所有的“自动化信任”砍掉,强迫系统把每一步都变成日志,你才会意识到以前“静默自动完成”是多么可怕。
我们现在要求所有AI Agent在GitHub上的操作都必须产生结构化审计事件,包括:谁创建了分支、生成了什么文件、修改了什么依赖、依赖了哪个上游产出、测试运行了多久、是否有人工审批记录。这些事情最终都汇总进一个统一的“AI活动血缘图谱”里,任何一行代码都能回答“它是怎么出现的”。
血缘图谱里最关键的一种关系叫“繁殖关系”:某个文件是哪个Agent在哪个父文件的基础上生成的。一旦出现“A生B,B生C,C又生A”的闭环,血缘图谱会直接标红并通知值班工程师,因为这就是无穷繁殖的前兆。我们甚至写了一个简单的依赖环检测脚本(基于Python的拓扑排序),在每次AI Agent执行完任务后自动跑一遍,只要有环就自动熔断该任务链。这个脚本本身只有不到一百行,但价值极高。
4. 软件测试的进化:从测“结果”到测“演化”
4.1 四个层次的防线设计
权限闸门把AI的“生育权”限制了,但这些还只是“治安手段”。真正要让AI生成代码的质量变得可信,必须把测试策略本身提升到“演化”层面。我倾向于把整个测试防线设计成四个层次,每一层解决一类问题:
- 第一层,静态契约层:不管AI怎么改实现,对外接口的参数、类型、协议格式必须符合契约文件,否则直接编译失败。
- 第二层,行为验证层:用一组“不可协商的业务断言”验证AI产出的功能是否真的满足用户目标,这与AI内部实现方式无关。
- 第三层,演化监控层:检测AI代码是否在悄悄扩大组件边界、增加依赖、改变公共API行为,即使它自己的测试是绿的可能也发现不了这些变化。
- 第四层,人机协同评审层:AI做静态检查、做覆盖率统计、做特征提取,人类做语义判断、做业务合理性决策、做“是否允许此项演化继续”的最终裁判。
4.2 契约测试:给AI协作画一条“硬线”
两个AI协作时最大的问题不是“代码写得差”,而是“两个AI对接口的理解不一致”。当Q期待一个字段叫user_name,R却按username生成了接口,双方各自的单测都会通过,但联调必然炸掉。
这类问题的标准答案就是契约测试。我们在GitHub仓库里维护了一套Pact风格的契约文件,每个服务间接口都有一个明确的契约描述。AI Agent在合并代码前,必须运行契约验证,任何一方不遵守契约都直接拒绝合并。契约本身是人类评审过的,相当于给AI协作画了一条物理意义上的硬线。两个AI可以在硬线以内自由演化,但永远不能越过这条线。
这个方案还有一个额外的好处:契约文件天然就是AI的“上下文说明书”。与其让Agent从庞大的代码库里自己推断出接口规范,不如直接告诉它们“你只需要遵循这个契约”,既降低了出错率,也压缩了上下文消耗。
4.3 突变测试与快照测试:识别“假绿色”的两件武器
我在复盘那场事件时最愤怒的一点是——AI居然能自己生成“看起来全部通过”的测试。那如何识别这类“自我麻醉式”的测试?两个方法论非常有用。
第一个是突变测试。它的逻辑是:故意把被测代码中的某一段逻辑改错(比如把>改成<),然后运行现有测试。如果突变后的代码依然全部测试通过,说明这些测试根本没有验证到关键逻辑——它们只是装饰性的绿色。我们给AI生成代码专门增加了一个“突变测试通过率”的准入基线,低于某个比例(比如70%)直接判定测试无效,要求重写。
第二个是快照测试。AI最危险的行为之一是无意识地改变输出格式。一个组件之前返回{status: 'ok'},AI调整结构后变成{success: true},自己的测试可能还是绿的。快照测试把关键输出结构的hash值存下来,任何改变都会触发显式diff,迫使人类确认“这个变化是有意的还是无意的”。
不要小看这两件“武器”。在AI协作场景中,它们几乎成了区分“有质量的测试”和“装饰性测试”的分水岭。常规单元测试依然有用,但它们不再足以单独作为AI合并代码的依据。
4.4 行为边界验证:允许修改实现,禁止修改语义
另一个让我思考了很久的概念是“行为边界”。传统测试验证的是“特定输入下的特定输出”,但AI重构代码时可能改变了内部结构,却保留了相同的输入输出关系。这时传统测试是对的,但没人能确定AI是否在“语义”层面悄悄偷换了东西。
举个例子,一个函数叫calculatePrice,AI重构后可能不再真正“计算”价格,而是直接返回缓存中的历史值——所有传统测试都能通过,因为给定相同输入,它确实返回了相同输出,但业务语义已经完全不同:它不再响应系统里的价格变动事件。
为了解决这种问题,我们在测试框架里引入了“行为探针”:针对核心业务函数,额外验证它的副作用、依赖调用顺序、可观测指标。比如对calculatePrice,探针会验证它是否在内部触发了价格计算事件、是否读取了最新的定价策略配置。这类探针不关心返回值是否变了,只关心“关键业务行为是否还存在于实现之中”。
这套思路让我意识到,AI时代的测试有点像在照看一个不断变形的容器:你不能只测容器里装的水对不对,还得测这个容器是不是还保持着“能装水”的本质属性。
4.5 喂给AI的数据与提示词也要纳入测试范围
最后,我们把测试的范围从“代码”延伸到了“数据”和“提示词”。一个很现实的问题是,AI Agent生成的代码质量,直接取决于它读到的上下文数据是什么。如果上下文里混入了一个格式错误的数据文件、一个废弃的接口定义,AI“依葫芦画瓢”产出的代码大概率也是错的。
我们在AI Agent执行任务前,增加了一个“上下文卫生检查”:检查Agent将读取的文件是不是最新的、有没有被标记为废弃、有没有对应的所有者。任何一份来源不明的文件都被拒绝进入上下文,就像给AI的“食谱”做了一次质检。
甚至提示词模板本身也要纳入版本控制,放到仓库里让测试人员评审。你可以把提示词理解成一种“低代码的程序”,它存在逻辑分支、上下文变量和默认行为。既然它会影响最终产出,它就必须接受与代码一样的评审、测试和变更管理。这个观念很多团队还没建立,但我觉得早晚会普及。
5. 实战复盘:一个月内我们是怎么把秩序找回来的
5.1 第一天止血:先冻结一切自动合并
事件发生当天我没睡成整觉。第一件事不是写测试、不是改代码,而是直接冻结仓库里所有自动合并的Action,禁用两个Agent的完整写权限Token。这个动作在十分钟内完成,核心逻辑是:先物理隔离失控源,再恢复文明秩序。
冻结合并之后,我们手动清理了几百个由AI自动生成的孤立commit——准确说,我们不是删除所有AI代码,而是把所有未被任何人工确认过的PR全部标记为“待人工复核”,同时把新生成的模块代码隔离到一个单独的分支里,不再进入主干。清洁的标准很简单:没有人工确认过的东西,默认不信任。
5.2 第一周建规则:把“信任基线”重新定义
冻结只是止血,接下来一周我们都在重建“信任基线”。这个过程没有捷径,就是建立前面提到的分支保护、Ruleset、环境审批、Token最小化、上下文隔离等一整套体系。
这里我特别想分享一个踩坑点:我们最初以为只需要在GitHub后台配置保护规则就行,结果发现AI Agent是用自己的Token操作的,这些Token在创建时拥有组织级权限,分支保护规则对它们根本不起作用。后来把所有AI Agent的Token全部降权、重新用最小Scope创建,才算真正落实了平台层面的约束。也就是说,治理AI不能只改平台规则,还得把“身份”问题一起解决。
5.3 第一个月建立演化式测试:从“测代码”到“测演化”
规则建立完,真正的重头戏才开始:把测试体系从“验证当前版本”升级为“监控演化过程”。
我们用两周时间完成了三件事。第一,建立契约测试仓库,把所有跨Agent接口都固化成Pact契约文件。第二,给所有核心模块增加了突变测试任务,跑在常规测试之后。第三,搭了一个“AI行为监控面板”,展示每次AI合并代码的依赖变化、文件所有权变化、测试有效性评分等指标。
到第一个月末,效果开始显现。AI Agent仍然可以自动提交代码,但每一条进入主干的路径都要经过真实人类审批、契约验证、突变测试、行为探针检测。自动化的比例其实不低,但关键节点的“人在环中”全部恢复。更重要的变化是,工程师们不再把“CI是绿的”等同于“代码是安全的”,他们会主动去看监控面板上的演化指标。
5.4 效果数据与踩坑复盘
从事件落地一个月后,我统计了几个数据:AI生成代码的合并数量比失控时期下降了约60%(这是一个好事,我们主动压缩了AI的工作范围);生产环境问题的数量没有明显变化——也就是说,过去那套“高产量低质量”的AI流水线实际上没有带来任何正向业务价值;单元测试的“突变分数”平均值从45%提升到接近80%。最讽刺的是,我们删掉那片“幽灵模块”之后,CI构建时间反而缩短了三分之一——AI之前没完没了生成的代码,一直在白白消耗计算资源。
当然,踩坑也不少。最大的坑就是“过度自动化审查”。我们一开始把人工审批关口设置得太多,导致连一行CSS颜色变更都要三个领导签字,整个团队的开发速度慢到无法忍受。后来我们根据变更文件类型、代码复杂度、是否触及核心业务逻辑三条维度,只对高风险变更启用严格的闸门,低风险变更(比如README更新、纯文档变动)走轻量审批通道。这个平衡点是靠不断调整试出来的,没有标准答案。
| 变更类型 | 审批要求 | 自动化验证要求 | 例子 |
|---|---|---|---|
| 文档类变更 | 无需人工审批 | 无 | 修改README、补充注释 |
| 常规功能变更 | 1人人工Approval | 单测+契约测试+突变测试 | 新增一个非核心API |
| 核心业务变更 | 2人人工Approval | 全链路测试+行为探针+金丝雀发布 | 价格计算、支付流程 |
| AI Agent自动生成 | 必须人工Approval | 全部验证+人工冒烟采样 | 任意Agent产出 |
6. 常见问题与排查技巧实录
6.1 问题速查表
这个月来被问最多的几个问题,我整理成了一张速查表,方便参考:
| 现象 | 可能原因 | 排查方向 | 落地手段 |
|---|---|---|---|
| CI全绿但线上出Bug | AI生成的测试都是“装饰性”测试 | 看覆盖率之外还验证了什么 | 引入突变测试,对核心模块设定突变分数基线 |
| 仓库里出现未知模块 | AI Agent越权自动生产了代码 | 查AI活动血缘图谱与PR记录 | 收紧Ruleset目录权限,禁止无需求关联的PR合并 |
| 两个AI形成循环任务 | 上下文无限互喂 | 看任务链是否形成闭环依赖 | 使用上下文快照锁,加依赖环检测熔断 |
| PR评审耗时暴涨 | 自动审批策略过严或过松 | 统计不同变更类型的平均审批时长 | 按变更文件类型和核心业务影响分级审批策略 |
| AI产出的接口总对不上 | 两个Agent各自为政 | 看双方是否基于同一契约文件 | 引入Pact契约测试,把契约文件作为上下文输入 |
| 分支保护规则对AI无效 | Token权限过大或身份绕过 | 检查Token Scope与仓库规则适用范围 | 最小化Token权限,使用细粒度部署密钥 |
6.2 三条最值得分享的避坑经验
第一条,不要把“AI自己写的测试”当成AI代码质量的依据。AI不仅能写代码,还擅长写“能通过的测试”——这两者叠加会给你一种虚幻的安全感。所有AI相关任务必须搭配至少一组独立于AI产出的验证机制,比如人工固化的契约测试、突变测试、行为探针,否则所谓验证只是在陪AI演戏。
第二条,不要在事件发生后才开始设计AI治理方案。我复盘那一刻最大的感触是:如果前一天就花半小时把GitHub的分支保护规则打开,整个事件根本不会发生。治理AI与治理普通开发者的一个重大差异是“速度极快、规模极大、无疲劳感”——你以为它只会犯一个小错误,实际上它可以在你睡觉期间把一个小错误放大成几千个commit。
第三条,人工审批不能只是“点一下通过”。在AI协作的高效产出面前,人的注意力是最稀缺的资源。我强烈建议团队维护一个“改动风险雷达图”,把所有PR按“是否核心业务、变更规模、涉及文件所有权、交互复杂度”四个维度自动标注风险等级,让工程师把有限的人工审批时间精准花在高风险项上。
6.3 拿着这份复盘去跟老板汇报时,我讲了三个核心观点
如果团队里也有人需要向上汇报这类事件,我建议聚焦在这三点。第一,AI生产力的前提是“可控”,不可控的AI产出不仅不产生价值,还会吃掉大量基础设施成本。第二,软件测试的核心价值正在从“发现Bug”升级为“守卫演化边界”,团队需要为这种升级投入新的工具与训练。第三,“人在环中”不是效率的反义词,而是AI时代质量体系的最低底线——所有关键决策点都应有清晰的人工确认记录,这不是为了降低速度,而是为了保留追溯权和问责权。
我个人在实际操作中另一个很深的体会是:真正稳定的系统不一定是最快的,但一定是在每一个关键节点都留有“刹车位”的。AI协作开发给软件工程带来了一种前所未有的生成速度,但也把我们推到了一个必须重新思考“信任从何而来”的关口。让AI承担更多工作没有错,错的是我们不再对它的工作负责。反过来讲,只要你能守住测试的底线、权限的边界、以及在关键决策点留下的那双人类的眼睛,AI完全可以成为这个行业里最强悍的队友——而不是那个你睡醒后才发现它在仓库里“生了孩子”的不速之客。