B BROCENT

如何用Claude对你自己的源代码做敌意测试

一套在你自己拥有的代码上跑敌意AI排查的实操方法——怎样把提示框成能找出真实缺陷的样子、为什么没复现就什么都不算数,以及它永远抓不到什么。

光线昏暗的房间里,几台显示器上都显示着程序代码
简而言之: 让模型"审查一下这段代码",你会得到一份客客气气的总结。让它在一个具体的信任边界上、去打破一个具体的假设,你才会得到值得分诊的发现。两者都只花五分钟,但只有一个有用。让它奏效的纪律是:任何你没有复现过的发现都不算数。让它正当的纪律是:这是你自己的代码、你自己的系统、并且你有授权。

大多数软件从来没有被人蓄意攻击过。它被写它的人审查过,跑过构建流水线里的那些检查,然后就上线了——而它遇到的第一个真正带着敌意的读者,并不站在你这边。

由合格的人来做的渗透测试是这件事的正确答案,而它要花真金白银、也要排真实的档期。在"什么都不做"和"正式立项一次委托"之间,还有一个便宜的中间步骤:花一个下午,用一个非常擅长读陌生代码、并擅长就"它会怎么坏"提出假设的模型,去攻击你自己的代码。做对了,这能找出真实的缺陷。而按多数人的做法去做,它什么也找不到,还让所有人感觉安心了——那比不做更糟。

下面的一切都假定:代码是你的、系统是你的,或者你持有所有者的书面授权。这不是走形式——它是安全工作与另一回事之间的那条线,而且值得在动手之前就拿到白纸黑字,而不是在有人问起之后。

为什么"让AI审查一下这段代码"几乎什么也找不到

问题出在提示词上,不在模型上。

它没有目标,于是它去优化覆盖面。 被要求"审查"时,它返回的是那些对任何代码都永远成立的东西:错误处理可以更好、这个函数太长、建议加测试。全都对,但没有一条是漏洞。

它不知道哪些输入是攻击者可控的。 没有信任边界,一个字符串就只是一个字符串。同样的拼接,出现在一个启动脚本里无关紧要,出现在一个请求处理函数里则是严重问题,而文件本身没有任何东西告诉模型它正在看的是哪一种。

除非你另外交代,它默认是顺着你的。 "这看起来安全吗?"是一个邀请你被安慰的问题,而你会如愿。框架必须让"找到问题"成为成功的结果,而不是尴尬的结果。

孤立地看一个文件,恰恰丢掉了要紧的那部分。 谁调用了它、带着什么、代表谁、在哪些检查之后——这些上下文活在代码库的别处,而只审查这个文件,就是在审查一个片段。

敌意框架改变了什么

怎样提示Claude去攻击一个假设,而不是总结一个文件?

用一句话说出你想被打破的那个假设,然后要求它推翻。不是"审查这段鉴权代码",而是"这个接口假定调用方只能引用属于自己组织的订单ID——找出所有能让这个假定不成立的路径"。一次只打一个假设。目标越窄,输出越可用。

要一条可利用路径,而不是一个结论。 一条发现应该以序列的形式到达:这个输入、在这个状态下、由这个角色发出、产生这个结果。没有路径的主张,是一个打扮成发现的猜测;而"要路径"这个动作本身,就能在你动眼之前滤掉相当一部分。

给它"找不到"的许可。 明确地说:就这段代码而言、针对这个假设"找不到可行的攻击",是一个可接受且有用的回答。不这样说,那片空白就会被填满。

让它对照你自己的模型排序。 问它:这些发现里,攻击者真正会先试哪一条、为什么。它给出的理由往往比排序本身更有信息量,而且能暴露出模型在哪里误解了你的架构。

哪些上下文才真正改变答案?

四样,而它们的缺席正是多数尝试失败的原因。

信任边界——攻击者可控的数据从哪里进入,以及系统对这条线两侧的数据分别相信什么。认证与授权模型——调用方的身份如何被确立、权限在哪里被检查、检查被跳过时会发生什么。数据模型——什么是按租户隔离的、什么是按用户隔离的、什么根本没有隔离。威胁模型——一个有十二个具名用户的内部工具,和一个公开注册表单,值得完全不同的关注度。

把这些给它,它就在对你的系统推理。不给,它就会凭空造出一个看着合理的架构,然后审查它自己造的那个。

一次实操的敌意排查,逐步拆解

在提示任何东西之前,先建立目标模型

花半小时写下:入口点、角色、每个角色被允许做什么、你最不愿意丢的数据在哪里,以及那三个"一旦发现是错的、你会最难受"的假设。这份文档是整次排查的运行基准,而且即使你就此打住它也有价值——多数团队从没把它写下来过,而这本身就是问题的一部分。

一次只跑一个攻击假设

按边界、按假设逐个来。一个覆盖十个关注点的提示,会在十个上面都返回浅层输出;一个只覆盖一个的提示,返回的是你能动手的东西。把范围控制在"合在一起才讲得通"的代码上——一个处理函数,加上它依赖的中间件和数据访问,而不是整个仓库;整个仓库放不下,就算放得下也会稀释注意力。

刻意地更换攻击者。一个未认证的陌生人、一个属于另一个组织的已认证客户、一个令牌尚未过期的前员工,以及一个能重放自己一小时前合法发出过的请求的人——这是同一段代码的四种读者,而他们找到的东西不一样。

分诊:没复现之前,什么都不算数

每一条发现只能贴一个标签。已复现意味着你真的让那件坏事发生了——在测试里、在本地实例上,并且步骤写了下来。已推翻意味着你顺着路径追过了,它不存在。信息不足是一个暂存区,不是一个结论;一条在那里待了一周的发现,是一条没人相信的发现。

只有已复现的那些才变成工作。这条规则在第一轮时会显得严苛,而它正是这整件事值钱的全部原因。

敌意AI审查 vs 静态分析 vs 真正的渗透测试

  • 成本 — AI审查完胜。它的价格是一份订阅加一个下午。
  • 代码覆盖的广度 — 静态分析胜出。它在每一次构建上跑过所有东西,不需要谁来决定该看哪里。
  • 对意图和业务逻辑的理解 — AI审查明显胜出。扫描器无法知道"这条退款路径本就不该被客户走到";一个对照你的目标文档推理的模型可以。
  • 误报负担 — 静态分析和AI审查都输,只是输法不同。扫描器产出大量机械式误报,你会学会过滤;AI审查产出的更少,但可信得多。
  • 跨服务的链式利用 — 渗透测试完胜。把一个薄弱的重置流程和另一个服务里的信息泄露组合起来,是有经验的测试者会做的事,而另外两者根本不尝试。
  • 能拿给客户或审计看的保证 — 渗透测试胜出,而且差距很大。一份合格测试者出具的报告是证据;一段聊天记录不是。

请把它读成一个序列而不是一份菜单。先AI审查、再静态分析、最后委托,意味着那个昂贵的步骤不会被花在"你本来免费就能找到的东西"上。

误报问题

流畅、可信的散文是模型最强的输出,也是你最大的成本。有两种失败模式要紧,而它们在纸面上长得一模一样。

第一种,是一条准确地描述了某个真实漏洞类别的发现,而代码其实并不那样做——模型匹配到了一个形状,然后把后果叙述了出来。第二种,是一条技术上正确却不可达的发现,因为上游三层的一个检查早已把它挡住了。两者读起来都自信、具体、令人警觉。

还有一项人们会漏掉的代价:一个被你*修掉*的误报,比一个被你忽略的误报更糟。你改动了本来正常的代码、花掉了一次评审,还带着"系统比原来更安全了"的信念走开。请先复现。永远如此。

这件事永远抓不到什么

运行时和基础设施的错误配置。 权限设错的对象存储桶、对全世界开放的安全组、还挂着默认凭据的管理后台——这些都不在源码里。

任何你没有提供的代码,其中包括你所有的依赖。

跨服务的链式利用。 那个单独看无害、却能把一次困难攻击变成容易攻击的信息泄露,活在两个系统之间的缝隙里,而你是分开审查它们的。

外部人才看得出的业务逻辑滥用。 定价边界情况、退款流程、多步骤工作流里的竞态——其中一部分在代码里看得见,而最有价值的那些例子,只对"在想业务而不是在想文件"的人可见。

你的构建流水线和密钥处理,除非你刻意把它指过去,而几乎没人这么做。

这份清单,正是"这能取代渗透测试吗"的诚实答案是"不能"的原因,而把这句话说出来本身就是论点,不是免责声明。

把这件事做对:源码保密、授权,以及何时该让IT介入

在这变成日常之前,有三件事要先定下来。

第一,授权。你自己的代码、你自己的系统;如果其中任何一部分属于客户,请在动手之前拿到书面许可。当你走到"这些发现需要独立验证"的那一步——或者客户、保险公司、审计方要的是证据而不是保证时——那正是由持证测试者进行的渗透测试所提供的,包括开箱式(白盒)委托:测试者拿到架构细节,用和本文一样的方式工作,只是附带了责任。

第二,保密。源码通常是一家公司最敏感的资产,而这套工作流会把它送出你的环境。请读一读你所用那个具体产品层级的数据处理与训练条款,而不是靠假设,因为商业版和企业版通常与消费级不同,条款也会变。把凭据从你要粘贴的任何东西里剥掉——而如果含有有效密钥的代码已经进过任何外部工具,请轮换那个密钥,而不是去推理它是否被留存。

第三,这些发现之后怎么办。已复现的缺陷应该进到你其余工作被追踪的地方,并附上复现步骤;我们那篇把支持工单变成结构化缺陷报告讲的正是这个书写问题。我们的AI+支持服务帮你把这类工作建在公司账号和受治理的权限上,而不是某个开发者的个人登录上;我们的托管IT支持则覆盖这次排查往往会暴露出来的凭据轮换和权限卫生。Brocent自2007年在北京创立以来,一直在亚洲提供托管IT与安全服务,总部位于新加坡,并自2016年起设有香港办公室。

常见问题

把专有源码发给AI模型安全吗?

这取决于层级和服务商,而且这是一个应该刻意去做、而不是默认发生的决定。请核对你所用那个具体产品当前的数据处理与训练条款,优先选择条款就是为此而写的商业版或企业版,并把任何已被粘贴过的密钥视为已泄露。对真正敏感的系统,请限定离开你环境的范围,而不是粘贴整个仓库。

它的发现里通常有多少是真的?

预期第一轮里大部分是噪声,并且不要相信任何给出普适数字的人——这高度取决于你的提示方式、你的代码库,以及你提供了多少上下文。要紧的是测量你自己的比率:把"已复现"对"已推翻"记录几轮,你很快就能看出你的框架有没有奏效。

这能取代渗透测试吗?

不能。它只审查你给它看的代码、别无其他;它无法在它没见过的系统之间串联发现;而它的输出不是任何人会接受的证据。它是一种便宜的方式,让你在为昂贵的那一步付钱之前,先把明显的问题找出来修掉——而这恰恰让昂贵的那一步更值。

我们能把它跑进CI吗?

把它当作对变更代码的一道闸口,比当作对整个仓库的扫描要好得多。拿一份diff对照"与这次变更相关的安全假设"来审查,是有界而有用的;而在每次构建上跑一次无界的敌意排查,大约一周就会造成告警疲劳,最后以所有人彻底忽略它收场。

一条我们复现不出来的发现该怎么办?

把它连同推理一起留在一份清单里,等相关代码变动时再回头看。不要修它、不要向上汇报、也不要让它变成一个任务——一条未复现的发现是一个假设,而把假设当成缺陷来处理,正是团队对这整件事失去信心的方式。

模型需要拿到整个代码库才有用吗?

不需要,而且把所有东西都给它通常会让输出更糟。有帮助的是那一"片"对的东西——你正在测试的边界、它的调用方、以及中间的那些检查——外加你写下来的目标模型。这里精准胜过体量,这也正是"一次一个假设"比"一次扫一遍"更管用的原因。

从哪里开始

挑那个"一旦失效后果最糟"的假设:通常是"一个用户不能触及另一个组织的数据"。用一句话把它写下来,把那个处理函数以及它一路调到数据库为止的所有东西收集起来,然后要求给出所有能让它不成立的路径。接着,在告诉任何人之前,先把返回的东西复现一遍。把一个边界做扎实,比把整个仓库审一遍能教给你更多关于你自己系统的事,而且它给了你一个可以复用到下一个边界的形状。如果你更希望让持证测试者来验证这项工作,或者把它暴露出来的凭据与权限卫生问题妥善处理好,欢迎联系我们

分享:

立即采取行动

将这些洞察转化为您企业的IT路线图。

预约15分钟免费咨询,与我们的亚太IT专家交流。我们将评估您的现有环境,并在24小时内提供定制化IT发展路线图。

📋

免费清单

进入大中华区IT部署前必须检查的10项关键事项

PIPL合规、网络分段、双语服务台配置等——企业进入中国大陆第一天所需的完整IT准备清单。

获取清单 →

📬 亚太IT月报

中国合规动态、网络安全预警及亚太IT实践指南,每月一期。

不发垃圾邮件,随时可取消订阅。