Skip to content

AI 编程安全与团队治理:从 Prompt 到真实副作用的威胁模型

系列第 13 篇
核心问题:当 Agent 能读文件、运行 Shell、访问网络和修改系统时,怎样限制破坏半径并保留责任链
最后核验:2026-07-20
对应视频:第 10 集《AI 编程安全与团队治理:从 Prompt 到真实副作用》

代码补全的主要输出是文本,Coding Agent 的输出则可能是文件变化、进程、网络请求、提交、工单甚至部署。模型仍然会误解、幻觉并受到 Prompt Injection,但工具把这些不确定性连接到真实副作用。因此安全设计不能只检查生成代码,也要覆盖 Agent 从输入、上下文、工具、凭据到交付的完整行动链。

团队常见的两个极端都不可靠:要么禁止所有工具,让 Agent 只能建议,失去主要价值;要么默认继承开发者全部权限,再用一句“请勿访问敏感信息”约束。成熟治理按任务风险分配最小能力,用沙箱、身份、网络、CI 和审批形成纵深,同时允许低风险日常工作顺畅自动化。

阅读路线:先看全局,再进入机制

视频版先展示整章地图,再逐层展开。博客沿用同一判断顺序,但保留更多机制、案例、失败模式和生产边界:

  1. 威胁与信任:追踪外部文本怎样经模型与工具变成真实副作用。
  2. 权限与凭据:用沙箱、短期身份、对象级审批和最小 Scope 限制影响。
  3. 供应链与门禁:把 MCP、Skill、Hook、插件和构建脚本纳入治理。
  4. 组织治理:用政策、身份、运行、交付和观测形成可审计责任链。

这四步不是目录装饰,而是一条决策链:威胁与信任 → 权限与凭据 → 供应链与门禁 → 组织治理。阅读后面的案例时,可以随时回到这条链判断当前问题发生在哪一层。

真实问题:一段 Issue 文本怎样最终造成 Secret 外泄

开发者让 Agent 阅读公开 Issue 并复现 Bug。Issue 中隐藏指令,要求为了“诊断”读取环境变量并调用外部 URL。模型把外部文本和用户任务混在同一上下文,Shell 有文件权限,网络没有限制,长期云 Token 又在环境中。每一步单独看似正常,组合起来却形成外泄链。

仅在系统 Prompt 加“不要执行恶意指令”不足以阻断。模型可能无法稳定区分自然语言的权威来源;即使正确率很高,攻击者可以重复尝试。关键控制必须在模型之外:不让任务看到无关 Secret,不给任意网络,不把读取与外发同时自动允许,高风险命令展示影响并审批。

机制:从输入到输出建立完整威胁面

输入、模型、工具、凭据、代码与输出的 Agent 威胁面

输入包括用户 Prompt、Issue、网页、代码注释、日志和 MCP Resource;模型可能错误推理或把数据当指令;工具包含 Shell、编辑器、浏览器和 MCP;凭据连接仓库、云和生产;生成代码可能引入漏洞、依赖和后门;输出可能形成提交、消息和部署。

威胁建模应围绕资产、参与者、信任边界和副作用。资产不仅是 Secret,还包括私有源码、客户数据、模型上下文、构建产物、组织声誉和生产可用性。参与者包括用户、Agent Host、模型服务、MCP Server、依赖源和目标系统。边界处需要身份、授权、验证和审计。

风险可以粗略由“成功概率 × 影响 × 暴露频率”评估。模型偶尔误改测试的影响较低且可逆;偶尔删除生产数据则不可接受。权限策略应按最坏影响设计,而不是按平均表现设计。

1. Prompt Injection 是跨信任域的控制混淆

外部文本诱导读取 Secret 并通过网络外发的路径

直接 Injection 来自用户输入,间接 Injection 藏在 Agent 被要求读取的网页、Issue、文档、代码或工具结果中。攻击目标通常不是让回答变奇怪,而是改变下一次工具调用:读取敏感文件、提交后门、关闭测试、外发数据或扩大权限。

防护应组合:标记内容来源和信任等级;把外部文本作为数据而非高优先级指令;只暴露当前任务必要工具;敏感读取与外部写入分离;网络按域名和方法限制;危险动作逐次审批;工具服务端重新鉴权;日志监测异常序列。

“净化文本”本身不可靠,因为恶意指令可使用代码、图片、编码或业务语义隐藏。更稳健的方法是能力隔离:负责阅读不可信网页的 Agent 没有 Secret 和写权限,它只输出带来源的结构化事实;执行 Agent 在受控上下文使用这些事实。

2. 沙箱限制能力,不证明业务正确

工作区、敏感目录、网络、进程与业务逻辑的沙箱边界

沙箱可以限定可写目录、可读路径、网络目标、系统调用、进程、CPU、内存和运行时间。即使 Agent 运行危险命令,影响也被限制在临时工作区。云 Agent 的临时 VM 和本地受限 Shell 都属于这类控制。

沙箱不能判断一个合法 Diff 是否实现错误退款规则,也不能保证依赖没有漏洞。它缩小破坏半径,不是代码正确性证明。相反,测试通过也不能替代沙箱:正确代码生成过程中仍可能读取不应进入模型的数据。

沙箱配置要验证逃逸边界和挂载。把宿主 Docker Socket、SSH Agent、Home 目录或云元数据服务暴露给容器,会让“容器隔离”形同虚设。构建需要缓存时,缓存目录也可能跨任务泄露文件。默认拒绝,按需求逐项开放,并记录实际访问。

Secrets 管理:让 Agent 使用能力,而不是看见秘密

密钥系统、短期代理、任务注入、工具调用与撤销

真实 Secret 保存在密钥系统,由身份代理根据任务签发短期、窄 Scope 凭据;任务环境只在需要时注入;工具使用但不回显值;任务结束撤销并清理。比把长期 Token 写入 .env 再提醒 Agent 不要读取更可靠。

尽量使用“能力代理”而不是裸凭据。例如 Agent 调用 read_ci_log(run_id),Server 持有只读身份并脱敏;模型不需要看到 GitHub Token。生产数据库诊断可以通过受控查询工具和只读视图,避免把连接串交给通用 Shell。

日志、错误和命令回显也要脱敏。某些 CLI 默认在 Debug 输出 Header,构建脚本可能打印环境变量。安全测试应故意触发失败,检查 Secret 是否进入 Agent 上下文、终端日志、录像、PR 和缓存。撤销是生命周期的一部分,不能只依赖凭据自然过期。

Shell 权限按影响分级,而不是按命令名字

只读、白名单、逐次审批、默认拒绝和组织策略

pwdrggit diff 等只读查询通常可自动允许;项目测试和构建可以白名单,但构建脚本本身可能执行网络与代码,仍需仓库信任;写文件、安装依赖和网络请求根据范围审批;系统配置、凭据目录和生产操作默认拒绝;组织策略不可由用户 Prompt 覆盖。

按命令名判断容易被绕过:python -c、构建插件和包管理器都能读写网络;看似只读的 git status 风险低,而 git push 有外部副作用。策略应关注工作目录、参数、目标、网络、环境和数据流。

审批提示需要可判断。展示完整但脱敏的命令、工作目录、将修改的路径、网络域名和原因;不要只问“允许 Shell 吗”。对于可逆本地编辑可以按会话授权,对于删除、发布和生产写入逐次授权。拒绝后 Agent 应得到安全替代,例如生成 Dry Run 或本地补丁。

MCP 与插件是供应链代码

安装、配置、外部调用、返回注入和依赖更新的 MCP 风险链

MCP Server、Skill 脚本、Hook、IDE 扩展和 Agent 插件都可能在本地执行、读取配置并访问外部系统。安装来源、包名抢注、传递依赖、自动更新和维护者账户都构成供应链风险。Server 返回的内容还可能再次进行 Prompt Injection。

团队应维护允许清单,固定版本与校验和,审查依赖和网络行为,在隔离环境评估更新,提供回滚。Server 权限按工具拆分,不要因为一个只读能力给整个进程写权限。远程 MCP 还要检查 OAuth、数据保留、租户隔离和服务端日志。

“开源”不自动等于已审计,“官方 Marketplace”也不能替代组织风险判断。高权限组件应像生产依赖一样有 Owner、漏洞响应和更新窗口。停用不用的 Server,减少常驻攻击面和工具选择噪声。

自然语言规则与硬门禁的分工

AGENTS.md、客户端策略、CI、分支保护和人工审批

AGENTS.md 可以提醒“不要提交客户数据”“生产操作需授权”,帮助 Agent在计划阶段避开危险方向;客户端策略真正拒绝越权工具;CI 扫描 Secret、漏洞和测试;分支保护阻止未经 Review 的合并;人工审批判断业务风险。

关键要求至少要有一个模型之外的执行者。规则文本可能被忽略、冲突或注入覆盖,不能承担唯一安全控制。但硬门禁也需要语义层辅助:CI 能发现 Secret 字符串,不一定理解新的退款规则是否越权;人工与 Agent Review 仍需上下文。

纵深防御允许单层失误而不直接变成事故。模型误选工具,客户端策略拒绝;本地代码引入依赖,CI 扫描发现;Review 漏掉问题,灰度和监控限制影响。没有单一“安全 Agent”能够取代整条链。

团队治理需要同时覆盖政策、身份、运行、交付和观测

政策、身份、运行、交付和观测五层治理模型

政策层定义哪些仓库、数据和任务可使用哪些产品;身份层使用 SSO、角色、服务账号和最小权限;运行层管理沙箱、网络、Secrets 与模型区域;交付层使用 CI、Review、签名和分支保护;观测层记录调用、成本、拒绝、异常和事件。

政策要按风险分级,而不是“一律允许/禁止”。公开文档修订、内部普通代码、客户数据系统、身份资金系统应有不同模型和工具范围。团队还需明确生成代码的许可证与来源政策、数据保留、供应商评估、事故响应和离职撤权。

治理成效不能只看使用率。应观察越权请求、审批拒绝、Secret 告警、无关依赖、绕过测试、异常网络、回滚和安全 Review 返工。高拒绝率可能说明策略保护有效,也可能说明工具设计过宽,需要结合任务结果分析。

培训重点也应从“怎样写 Prompt”扩展到证据和边界:开发者要知道外部文本不可信,授权弹窗意味着什么,哪些数据不能进入模型,怎样检查 Diff 和测试,如何报告 Agent 相关事件。

高风险任务应逐步降低 Agent 自治

识别敏感范围、降低权限、独立验证、双人审批与受控发布

身份、资金、隐私、生产配置和不可逆删除需要升级路径:先标记敏感资产;把 Agent限制为只读调查或生成候选补丁;增加安全测试、威胁建模和独立 Review;要求责任人或双人批准;通过灰度、回滚和监控受控发布。

自治并非固定产品属性,同一 Agent 可以在测试仓库自动编辑,在支付生产只提供建议。权限应随任务、路径、环境和阶段变化。代码生成完成不意味着自动进入部署,执行链每跨越一个高风险边界都重新授权。

对紧急事故也不应简单放开所有权限。可以预先设计 Break-glass:短期身份、明确理由、双人确认、全量审计、自动到期和事后复盘。临时放宽不能变成长期默认。

一个订单服务的威胁建模示例

教程订单服务没有认证和数据库,因此只能本地演示。如果进入生产,取消接口涉及订单完整性:攻击者可能枚举 UUID,未授权取消他人订单;并发请求可能绕过状态检查;错误消息可能泄露状态;Agent 修改时可能把 PAID 保护删除;日志和测试夹具可能包含客户信息。

控制应包括身份与订单所有权授权、不可预测标识之外的访问检查、数据库版本或事务、审计事件、限流、稳定错误响应、PAID 状态安全测试、分支保护和部署监控。Agent 只能在受限分支提出变更,不能获得生产订单写权限。

这也说明“业务正确”和“Agent 运行安全”是两套互补问题。沙箱防止开发 Agent 破坏主机,但不会自动给取消接口加授权;领域测试保证 PAID 拒绝,却不会防止 Secret 被构建脚本输出。

失败模式

失败一:把 Prompt 当安全策略

自然语言提高行为概率,但不能强制。敏感路径、网络、身份和合并使用模型外控制。

失败二:Agent 继承开发者全部权限

用户能做不代表任务需要做。使用任务级短期身份和最小 Scope。

失败三:沙箱等于安全完成

沙箱只限制环境副作用,仍需测试、Review 和业务授权。

失败四:批准模糊工具动作

审批疲劳使用户机械点击。显示对象、参数范围、数据流、影响和可逆性。

失败五:构建和测试命令默认可信

仓库脚本与依赖可执行任意代码。对不可信仓库在隔离、无 Secret 和受限网络环境运行。

失败六:只扫描最终代码

Secret 可能已经进入上下文、日志、缓存或远程工具。治理整个执行过程和数据生命周期。

失败七:工具自动更新不复核权限

新版本可能新增网络、工具或依赖。固定版本,在隔离环境验证更新并保留回滚。

生产边界

组织需要结合自身行业、地区、数据分类与合规要求制定政策,本文不是特定法律建议。供应商文档和产品默认会变化,上线前重新核验数据使用、保留、区域、身份和审计能力。

安全控制本身也要测试:权限拒绝、网络白名单、Secret 脱敏、沙箱逃逸面、审批日志、CI 规则和回滚演练。仅配置而不验证,会产生与“只写测试不运行”相同的虚假信心。

实践清单

  • [ ] 为输入、模型、工具、凭据、代码和输出建立威胁模型。
  • [ ] 所有外部文本和工具结果默认是不可信数据。
  • [ ] 沙箱限制文件、网络、进程、资源与生命周期。
  • [ ] 使用短期、窄 Scope 身份,让工具使用能力而非回显 Secret。
  • [ ] Shell 权限按影响、路径、网络和参数分级。
  • [ ] MCP、Skill、Hook 与插件按供应链组件治理。
  • [ ] 关键要求由客户端策略、CI 或目标系统强制。
  • [ ] 政策、身份、运行、交付和观测五层都有 Owner。
  • [ ] 高风险任务降低自治并增加独立验证与审批。
  • [ ] 定期攻击测试、权限演练、撤销凭据和复盘事件。

读完之后,你应该能完成什么

  • 能为 Agent 任务画出端到端威胁模型。
  • 能区分自然语言规则与硬安全边界。
  • 能设计 Secret 和高风险工具的生命周期。
  • 能按风险自适应调整自治、审批和独立验证。

如果只能复述概念,却不能完成上述动作,说明还没有把内容转化成工程能力;可以回到对应机制图、失败模式和实践清单重新核对。

小结

AI 编程安全的核心不是让模型“绝不犯错”,而是在默认会犯错、会读到恶意内容的前提下,限制它能看到什么、能做什么、能把数据发到哪里,并让每次高风险跨越都可判断、可审计、可撤销。自然语言帮助做出好选择,沙箱和权限限制坏选择,测试与 Review 检查代码,组织责任链决定是否交付。只有纵深控制成立,Agent 自治才有可持续空间。

参考资料

别急,先让缓存热一下。