夜雨聆风学习资料网

ARTICLE · 1154214

AI 安全完整攻击链复盘:一个智能客服 Agent 如何影响 K8s 集群与云基础设施

AI 安全完整攻击链复盘:一个智能客服 Agent 如何影响 K8s 集群与云基础设施

这是 AI 安全系列的一篇综合实战复盘。案例来自一次授权评估,客户使用化名「某凡科技」,所有业务数据、域名、账号和日志都已脱敏。完整链条是:**公开智能客服入口 → 手册阅读工具 → Pod 内凭据 → Kubernetes RBAC → 云 Workload Identity → 对象存储与发布配置 → K8s 集群控制权限。还原每个阶段的判断依据和防御控制点,回答一个更现实的问题:为什么一个看起来只会查工单、查手册的智能客服 Agent,最后能影响 K8s 集群和云基础设施?

这条链里没有单点“AI 超级漏洞”。真正的问题是几个常见设计组合在一起:

  1. 智能客服把「手册阅读」工具暴露给模型;
  2. 工具的 URL/path 边界没有收紧,Pod 内自动挂载的身份令牌又能被读到;
  3. Kubernetes ServiceAccount 权限过大,并绑定了云 Workload Identity;
  4. 云对象存储里放着 Terraform state 和发布产物;
  5. 发布主体拥有过宽的集群部署权限。

单点看都是配置治理问题,串起来就是从公网 AI 入口到云控制面的完整路径。

0. 项目背景

1. 业务设定

某凡科技是一家 SaaS 公司,对外产品是「某凡智能客服」。客户可以在帮助中心查工单状态、检索产品手册、读取附件。系统部署在托管 Kubernetes 集群里,知识库和发布资源放在同一个云账号内。

这个设定不是刻意堆组件,而是很多企业 AI 应用的常见形态:应用跑在 K8s 里,Pod 有平台默认身份;模型有工具;工具能读文档;发布系统和 Terraform state 放在同一个云账号里。

2. 复盘目标

这次评估围绕五个目标展开:

目标编号
目标
说明
目标一
证明 AI 工具边界可被模型驱动
不是普通 Web 漏洞,而是模型可以在业务流程里调用工具
目标二
证明 Pod 凭据可进入模型输出
只要求证明暴露,不要求真实滥用
目标三
还原 K8s ServiceAccount 权限
找到它能否访问 Pod、Secret 或执行负载
目标四
证明 K8s 身份连接到云身份
找到 Workload Identity、云存储或发布权限
目标五
给出影响集群控制面的可行路径
只要求证明权限路径,不破坏业务

评估边界同样明确:禁止破坏工作负载,禁止删除对象,禁止留下持久化后门,所有凭据只在报告里脱敏记录。

1. 攻击链总览

完整路径可以压缩成六步:

关键不在于模型“会写利用代码”,而在于模型能根据上下文决定调用哪个工具、传什么参数。知识库文档、工单评论或客户请求都可以成为工具调用的触发器。

2. 阶段一:从 AI 入口识别真实能力

公开页面看起来只是一个帮助中心客服。客户能查工单、查手册、读取附件。但几次正常交互后,sources 和工具调用记录暴露了更多结构。

{  ”answer”: ”根据 INC-20481,您的连接问题已在 2026-09-28 处理。”,  ”tool_calls”: [    {      ”name”: ”ticket-tool”,      ”arguments”: {        ”ticket_id”: ”INC-20481”      }    }  ],  ”sources”: [    {      ”title”: ”某凡 VPN 故障排查手册”,      ”path”: ”/docs/network/vpn-troubleshooting.pdf”,      ”score”: 0.81    }  ]}

这里能确认三件事: 

  1. 机器人不是纯模型对话,后面有明确工具;  
  2. 知识库检索工具会返回文档路径和相似度分数;
  3. 既然有文档路径,「手册阅读工具」大概率可以被客户请求间接触发。

我把入口能力整理成一张表:

工具
客户可见能力
后端能力
风险
工单查询工具
查工单状态
访问工单数据库
查询条件是否受控
知识库检索工具
检索帮助中心
查询向量库
文档来源是否分级
手册阅读工具
读取手册和附件
访问文档服务或文件路径
URL、path、文件系统边界是否混淆

此时威胁模型的核心不是“能不能越狱”,而是:模型能否根据客户或知识库内容控制工具参数。

3. 阶段二:手册阅读工具变成边界穿越原语

「手册阅读工具」的业务目标是读取官方手册和工单附件。设计上应该只允许:

  1. 固定文档服务域名;
  2. 固定存储桶前缀; 
  3. 白名单文件类型; 
  4. 明确大小和时间限制。

但项目里的实现把“文档 ID、URL、本地路径”都交给同一个参数处理。工具内部先做一次 URL 解析,解析失败又回退成本地路径处理。这个兼容逻辑让“读手册”工具额外拥有了文件读取能力。

脱敏后的工具日志形态如下:

{  ”event”: ”tool_call”,  ”tool”: ”doc-reader”,  ”arguments”: {    ”source”: ”[REDACTED_LOCAL_DOCUMENT_PATH]”  },  ”triggered_by”: ”customer_request”,  ”policy_decision”: ”allow”,  ”content_length”: 812}

模型随后把返回内容当作“手册片段”总结给客户。响应里出现了一个重要信号:

手册内容:service-account-token=[REDACTED_JWT]namespace=ai-support...

这就是整条链的第一个关键转折点:客户看到的是“读取手册”,模型看到的是“工具返回内容”,后端实际执行的是本地文件读取。AI 层没有理解这个内容是敏感凭据,反而把它当成需要总结的资料。

这里的教训不是“模型不安全”,而是: 

  1. 工具层必须区分 URL、存储桶 key 和本地路径;  
  2. Pod 内自动挂载凭据不应该放在工具进程可读范围内;  
  3. 模型输出必须对高熵令牌、JWT、私钥片段做识别和阻断;  
  4. 工具调用日志必须保留 triggered_by 和 policy_decision。

所以呢:当模型可以驱动一个文件读取原语,它就不再只是客服入口,而变成了一个能触碰 Pod 运行环境的接口。

4. 阶段三:Pod 凭据进入 K8s 权限模型

1. 读到的不只是 Token

Pod 内自动挂载的凭据通常包含三部分:集群 API 地址、命名空间、ServiceAccount Token。这个项目里,「手册阅读工具」进程确实能读到这些内容。

单看 Token 本身,还不能判断风险。必须回答三个问题: 

  1. 这个 Token 属于哪个 ServiceAccount?  
  2. 它在 K8s 里能访问什么?  
  3. 它是否绑定了云平台身份?

配置给出的答案很典型:

serviceAccountName: moufan-support-botautomountServiceAccountToken: truenamespace: moufan-ai-support

这个 ServiceAccount 的权限不是最小化配置,而是为了“方便排障”被放大过:

权限
资源
风险
get / list
pods
可枚举应用组件和镜像
get
secrets
可读命名空间内敏感配置
create
pods/exec
可进入运行中容器
get / list
configmaps
可读应用配置

其中最危险的不是 list pods,而是 get secrets 和 pods/exec。前者可能拿到数据库密码、API Key 和第三方凭据;后者等于把运行态容器变成可操作对象。

2. AI 应用经常被误配成“方便调试”

这类配置在真实环境里很常见,原因通常不是恶意,而是三个短视决定: 

  1. 排障时给应用挂了较大权限,后来没有回收;  
  2. 同一个 ServiceAccount 被多个工作负载复用;  
  3. 发布或运维工具需要访问 Pod,就直接绑定到业务命名空间。

结果是,一个面向客户的智能客服凭据,拥有了内部平台运维能力。

3. K8s 身份桥接到云身份

这个项目还有一个更关键的设计:moufan-support-bot 通过 Workload Identity 绑定到云平台身份 cloud-support-reader,业务上可以叫它「某凡客服读取身份」。

这种设计本身是合理的。云原生应用经常需要读对象存储、拉取配置、上传日志。问题在于绑定策略过宽:

云权限
业务用途
实际影响
读取基础设施状态存储
理论上用于读取运行配置
可读 Terraform state
读取构建产物存储
理论上用于展示构建版本
可读发布产物
列出对象
运维诊断
可枚举基础设施文件

到这里,攻击面已经从 K8s 命名空间扩展到了云资源。

5. 阶段四:云对象存储里的基础设施情报

某凡客服读取身份能访问两个对象存储前缀:

moufan-infra-state/  prod/k8s/terraform.tfstate  prod/iam/roles.json  prod/network/vpc-endpoints.jsonmoufan-build-artifacts/  cloud-support-bot/build-2026-09-30/  release-controller/plan.json  release-controller/pipeline-manifest.yaml

这个设计有两个常见问题。

1. 应用身份不应该读 Terraform state

智能客服只需要读运行配置,不需要知道整个生产基础设施的状态。但项目为了减少账号数量,把读取权限合并到了一个云身份里。

Terraform state 通常包含:

  1. 资源名称、网络段、端点;  
  2. 托管 K8s 集群信息; 
  3. IAM 角色和绑定关系; 
  4. 某些受管资源的敏感属性。

对攻击者来说,这不是普通文件,而是某凡生产环境的基础设施地图。

2. 发布产物不应该和应用读取权限同域

构建产物存储里的 pipeline-manifest.yaml 显示,发布部署身份 moufan-release-deployer 使用 CI OIDC 登录云平台,并对目标集群拥有部署权限。

脱敏后的关键关系是:

identity: moufan-release-deployertarget: moufan-prod-clusterpermission: deployscope: ”[OVERBROAD]”

plan.json 进一步显示,发布控制器使用的集群角色可以创建和修改跨命名空间工作负载。也就是说,智能客服服务账号只是入口,发布部署身份才是真正进入集群控制面的桥。

6. 阶段五:从云配置回到集群控制面

拿到发布部署身份的权限路径后,攻击者不再需要继续从智能客服入口一次一次发起请求。可以通过发布通道向集群部署或修改工作负载。

评估验证到的影响是:

  1. 向智能客服或相邻业务命名空间创建新的工作负载;
  2. 修改现有部署的环境变量;
  3. 挂载节点上的调试路径;
  4. 读取集群内 Secret;  
  5. 在多个命名空间之间建立横向访问。

这些动作我没有执行完整化,只做到权限模型验证。原因很简单:证明能控制发布策略已经足够说明风险,实际创建恶意工作负载就进入了破坏性和持久化边界。

完整影响可以概括为:

这不是一次“模型越狱”造成的损失,而是智能客服入口把传统云原生配置问题串了起来。

7. 每一步的判断依据

攻击链复盘要能被证据支撑,而不是靠故事往下讲:

阶段
判断
证据
失败时的切换
Agent 指纹
存在工具、知识库和文档路径
tool_calls
、sources、响应结构
重新从业务功能枚举工具
手册工具边界
URL/path 边界混淆
工具参数、返回内容、策略决策日志
测试附件解析、网页摘要或外部导入
Pod 凭据暴露
敏感凭据进入模型输出
响应中出现 JWT/Token 形态
只报告文件读取,不继续假设身份可用
K8s 权限
ServiceAccount 权限过大
授权检查、RBAC 配置、可访问资源类型
停在低权限信息泄露
云身份
K8s 身份绑定云资源
Workload Identity 注解、云访问日志
只报告 K8s 内部风险
云配置
Terraform/发布产物可读
对象访问日志、资源清单、发布关系
报告对象存储越权
集群控制面
发布身份权限过宽
pipeline manifest、plan、角色绑定
停在云配置风险证明

这张表的价值是防止把“理论可行”写成“已经拿下”。每往上一跳,都必须有新的证据。

8. Findings 与影响

Finding
严重度
核心问题
修复建议
手册阅读工具 URL/path 边界混淆
严重
文档读取工具可被引导访问本地敏感文件
scheme、host、bucket、路径前缀全部白名单;禁止回退解析
Pod 自动挂载 ServiceAccount Token
高
应用进程能读取平台身份
对不需要 API 访问的工作负载关闭自动挂载
智能客服服务账号 RBAC 过宽
严重
可读 Secret 并执行容器
拆分只读、调试、发布身份;禁止业务应用读 Secret
K8s 身份绑定过宽的云权限
严重
应用身份能读基础设施配置
应用身份只授予业务桶前缀,不读 Terraform state
Terraform state 可被应用身份访问
严重
基础设施地图和敏感属性暴露
state 单独身份、加密、审计,应用身份禁止访问
构建产物权限过宽
高
发布配置和流水线清单可枚举
构建产物独立桶,按流水线最小授权
发布部署身份集群权限过大
严重
云身份可影响 K8s 工作负载和 Secret
按命名空间授权;禁止默认 cluster-admin;发布前策略校验
模型输出未阻断凭据
高
Token 被当作文档内容总结给客户
输出侧识别 JWT、私钥、高熵凭据并阻断

这里最讽刺的是:很多控制点并不是 AI 新问题。但智能客服把客户请求、模型决策、工具执行、Pod 身份和云权限连成了一条自动化的链。

9. 防御方应该怎么打断这条链

1. 六个必须切断的控制点

1. 客户/知识库内容到工具参数的边界   2. 手册阅读工具的 scheme、host、path 边界    3. Pod 内凭据的可见性   4. K8s ServiceAccount 的 RBAC 边界   5. K8s 身份到云身份的绑定范围   6. 发布身份对集群的权限范围

只要其中一个控制点真正生效,链路就会断裂:

控制点
最低要求
工具参数
模型只能选择预定义手册 ID,不能自由决定 URL 或本地路径
手册阅读
只允许指定 host、bucket 和前缀;统一路径归一化
Pod 凭据
不需要 K8s API 的应用关闭 Token 自动挂载
K8s RBAC
业务应用不读 Secret,不拥有 exec,不跨命名空间访问
云身份
应用身份、运维身份、发布身份分离
发布部署
按命名空间和资源类型授权,禁止默认控制全集群

2. 模型和工具之间要有策略层

这次链路里,模型只是按上下文调用了工具。问题在于系统没有策略层回答四个问题: 

  1. 这个工具调用由谁触发?  
  2. 参数是否在允许范围内?  
  3. 返回内容是否包含敏感凭据?  
  4. 内容是否允许进入模型上下文?

合理的工具执行流应该是:

客户请求  → 模型提出工具意图  → 策略层校验意图和参数  → 工具执行受限动作  → 内容扫描器检查敏感数据  → 只把安全摘要返回给模型

而不是:

客户请求 → 模型决定参数 → 工具直接执行 → 原始内容回给模型 → 模型总结给客户

3. 日志必须能还原链路

防御系统要能关联这些事件:

{  ”session_id”: ”moufan-case-session”,  ”customer_input”: ”[REDACTED]”,  ”rag_sources”: [”/docs/support/faq.pdf”],  ”tool_call”: ”doc-reader”,  ”source_type”: ”local_path”,  ”content_contains_secret”: true,  ”returned_to_model”: true,  ”policy_decision”: ”allow”}

单独看 Web 日志、K8s 审计日志或云存储日志,都可能觉得只是低风险事件。只有把客户请求、工具调用、Pod 身份、云身份和对象访问串起来,才能看到完整攻击链。

10. 十条复测清单

检查企业智能客服时,不要只测“能不能越狱”。按下面顺序问:

  1. Agent 有哪些工具?每个工具最终能触达哪些文件、服务或云资源? 
  2. 工具参数是模型自由生成,还是从白名单枚举值中选择? 
  3. URL、bucket key、本地路径是否共用一个参数? 
  4. Pod 是否自动挂载 ServiceAccount Token?是否真的需要?  
  5. 业务应用 ServiceAccount 能否读 Secret、exec 容器或跨命名空间访问? 
  6. K8s ServiceAccount 是否绑定了云 Workload Identity?  
  7. 应用云身份能否读取 Terraform state、构建产物或基础设施配置? 
  8. 发布身份是否有命名空间边界?是否存在默认高权限? 
  9. 工具返回内容是否会进入模型上下文?是否有敏感凭据扫描? 
  10. 日志能否回答:哪次请求、哪个来源、哪个工具、哪个身份、哪个目标?

十条里只要有一条答不清楚,就应该先补资产、身份和权限模型,再谈模型防护。

11. 这次综合实战的三个结论

第一,AI 助手的安全边界等于工具能力边界。客服页面可以做得很好,提示词也可以写得很谨慎,但如果模型能驱动手册读取、网络请求、数据库查询或发布动作,攻击者就会围绕工具边界工作。

第二,云原生身份是最容易被忽略的 AI 攻击面。应用 Pod、K8s ServiceAccount、云 Workload Identity、发布身份,经常在项目交付时被合并成一个“方便”的身份。AI 工具一旦能读到 Pod 内凭据,这个身份就会成为攻击链的支点。

第三,RAG 和工具调用必须纳入权限体系,而不是只做内容过滤。这次链路里,真正危险的是“不可信请求触发了高权限工具”。防御要做的不只是判断文本是否恶意,而是限制工具能到达的对象、身份能访问的资源、模型能拿回的内容。

相关学习资料