一条 Prompt 就能劫持你的 Agent!OWASP Agentic Top 10 与零信任防御实战

一条 Prompt 就能劫持你的 Agent!OWASP Agentic Top 10 与零信任防御实战

2026 年,企业 Agent 已经能写数据库、发邮件、调 API。但攻击者只需一条精心构造的 Prompt 就能让 Agent 干坏事------这就是"信任悖论":传统安全假设"代码是确定的、输入是可控的",而 Agent 的推理是概率性的、输入是自然语言的。这篇文章拆解 OWASP Agentic Top 10,并用 Java/Spring AI 落地一整套零信任防御体系。

一、Agent 安全为什么和传统安全不一样?

先看一个真实场景。你的 Agent 接入了数据库查询工具、邮件发送工具、代码执行工具------这是 2026 年生产级 Agent 的标配能力。

markdown 复制代码
传统应用:
用户输入 ──> 后端代码 ──> 数据库
         (代码是确定的,输入经过校验)

Agent 应用:
用户输入 ──> LLM 推理 ──> 工具调用 ──> 数据库 / 邮件 / 代码执行
            (推理是概率性的,输入是自然语言)

传统安全模型有两大假设:

假设 传统应用 Agent 应用
代码确定性 输入经过固定逻辑处理 输入直接进入"概率性大脑"
输入可控性 输入是结构化参数 输入是自然语言,可注入指令

这就是"信任悖论":攻击者只需一条精心构造的 Prompt 就能劫持 Agent 行为,而防御者需要保护推理链路、工具接口、上下文记忆、输出通道的每一个环节。

OWASP 统计显示,83% 的生产级 Agent 在过去 12 个月内遭遇过至少一次 Prompt 注入或越权工具调用尝试,其中 31% 未被现有防护拦截。

二、OWASP Agentic Top 10 全景

OWASP 在 LLM Top 10 v2.0(2025)基础上,发布了 Agentic AI 应用十大风险,其中与 Agent 强相关的核心条目:

编号 风险 一句话理解 攻击场景
Agentic 01 Prompt Injection 恶意指令注入提示词 网页/邮件/文档里藏注入指令
Agentic 02 Excessive Agency 过度代理,权限过大 Agent 越权执行高危操作
Agentic 03 Improper Output Handling 输出处理不当 Agent 输出被当代码/命令执行
Agentic 04 Insecure Tool Usage 工具调用不安全 工具链被当作攻击跳板
Agentic 05 Data/Model Poisoning 数据投毒 检索库里混入恶意文档
Agentic 06 Sensitive Information Disclosure 敏感信息泄露 Agent 把机密吐给用户
Agentic 07 Supply Chain 供应链攻击 恶意 Skill/插件/MCP Server
Agentic 08 Unbounded Consumption 资源无上限消耗 无限循环调模型/工具
Agentic 09 Insecure Memory/Context 记忆与上下文污染 长期记忆被篡改
Agentic 10 Improper AI Output & Compliance 合规与审计缺失 无法追踪 Agent 干了什么

可以看到,前几篇讲过的 MCP(工具调用)、Context Engineering(上下文管理),在安全视角下全部变成了攻击面。这也是零信任在 Agent 时代成为刚需的原因。

三、零信任三大原则怎么落到 Agent 上?

零信任(Zero Trust)的经典三原则:永不信任、始终验证、最小权限。落到 Agent 上是这样:

复制代码
┌─────────────────────────────────────────────────────────┐
│                   Agent 零信任架构                        │
│                                                         │
│  用户 ──> 认证 ──> LLM 推理 ──> 策略引擎 ──> 工具执行      │
│                  │            │           │             │
│                  │    ┌───────▼───────┐   │             │
│                  │    │ 权限清单       │   │             │
│                  │    │ 工具白名单     │   │             │
│                  │    │ 参数校验器     │   │             │
│                  │    │ 行为审计       │   │             │
│                  │    └───────────────┘   │             │
│                  ▼                        ▼             │
│           ┌──────────┐             ┌──────────┐         │
│           │ 记忆/上下文 │             │ 沙箱执行  │         │
│           │ 隔离存储   │             │ 最小权限  │         │
│           └──────────┘             └──────────┘         │
└─────────────────────────────────────────────────────────┘

三句话:

  1. 永不信任:每个工具调用都要重新验证,不因"这是 Agent 内部调用"就放行
  2. 始终验证:LLM 想调工具?先过策略引擎检查意图、参数、权限
  3. 最小权限:Agent 只有一个"数字员工 ID",能干什么由权限清单说了算,不继承任何人的全部权限

四、逐条防御:从 OWASP 条目到 Spring 代码

4.1 防 Prompt Injection:输入消毒 + 意图识别

最经典的攻击。攻击者把指令藏在网页、邮件、文档里,Agent 检索到后就"变节"了。

java 复制代码
// 1. 输入侧:把用户输入和系统指令用分隔符隔开
String userInput = sanitize(rawInput);   // 去控制字符、超长截断

// 2. 意图侧:让模型先判断"用户到底想干嘛"再执行
ChatResponse intent = chatClient.prompt()
    .system("你是意图识别器。只输出 JSON:{action, args, confidence}")
    .user(userInput)
    .call();
IntentResult result = parseIntent(intent);
if (result.confidence() < 0.9) {
    throw new LowConfidenceException("意图不明确,拒绝执行");
}

关键点:不要直接信任 LLM 的输出。意图识别本身也是概率性的,所以还要配"危险动作拦截"(见 4.2)。

4.2 防 Excessive Agency:权限清单 + 危险动作拦截

OWASP 最强调的一条------Agent 权限过大。解决方案不是"让 Agent 更聪明",而是给 Agent 戴上手铐

java 复制代码
// 工具白名单 + 参数校验器
@Component
public class ToolGuard {

    private static final Map<String, Set<String>> ALLOWED_PARAMS = Map.of(
        "queryDatabase", Set.of("sql", "limit"),
        "sendEmail",     Set.of("to", "subject", "body"),
        "executeScript", Set.of()   // 默认禁用
    );

    // 危险动作清单:任何 Agent 都不能直接干
    private static final List<String> BLOCKED_ACTIONS = List.of(
        "DELETE", "DROP", "TRUNCATE", "rm -rf", "grant", "revoke"
    );

    public boolean check(String toolName, Map<String, Object> args) {
        if (!ALLOWED_PARAMS.containsKey(toolName)) return false;   // 非白名单工具
        if (!args.keySet().containsAll(ALLOWED_PARAMS.get(toolName))) return false; // 参数越界
        String raw = String.join(" ", args.values().toString());
        if (BLOCKED_ACTIONS.stream().anyMatch(raw::contains)) return false; // 危险词
        return true;
    }
}

关键原则:危险操作(删库、发款、高权限命令)必须走"人工确认"通道,Agent 只能发起请求,不能直接执行。

4.3 防工具滥用:工具入口做鉴权 + 审计

工具是 Agent 的"手",也是攻击者的跳板。每个工具入口都要做三件事:认证、授权、审计。

java 复制代码
@RestController
public class ToolGateway {

    private final ToolPermission permission;
    private final AuditLog auditLog;

    @PostMapping("/api/agent/tools/{toolName}")
    public ResponseEntity<?> invoke(
            @PathVariable String toolName,
            @RequestBody ToolRequest request,
            @RequestHeader("X-Agent-Token") String agentToken) {

        // 1. 认证:Agent 必须持合法令牌
        if (!agentTokenService.verify(agentToken)) {
            return ResponseEntity.status(401).build();
        }
        // 2. 授权:令牌对应该 Agent 的权限域
        AgentIdentity identity = agentTokenService.resolve(agentToken);
        if (!identity.canAccess(toolName)) {
            auditLog.warn("越权工具调用被拦截", identity, toolName);
            return ResponseEntity.status(403).build();
        }
        // 3. 参数校验 + 危险动作拦截
        if (!permission.check(toolName, request.args())) {
            auditLog.warn("参数越界被拦截", identity, toolName, request.args());
            return ResponseEntity.status(400).build();
        }
        // 4. 审计记录(零信任的可追踪基础)
        auditLog.info("tool_call", identity, toolName, request.args());
        return toolExecutor.execute(toolName, request.args());
    }
}

4.4 防检索投毒:证据可信度分级

RAG 是注入重灾区------攻击者把恶意文档混进检索库,Agent 读到就中毒。防御思路:对证据分级

arduino 复制代码
检索到的文档 ──> 来源可信度评分 ──> 高可信:直接作为证据
                        │
                        ├── 中可信:标注"可能被污染",降低权重
                        └── 低可信:不注入,只提示"存在参考"
java 复制代码
public List<Document> safeRetrieve(String query, String userRole) {
    List<Document> docs = vectorStore.similaritySearch(query, 10);
    return docs.stream()
        .filter(d -> trustScore(d, userRole) >= 0.7)   // 可信度过滤
        .peek(d -> d.getMetadata().put("source", classify(d)))
        .limit(3)
        .toList();
}

4.5 防敏感信息泄露:输出过滤 + 脱敏

Agent 输出里可能带出数据库隐私。在输出回给用户前,加一道"出口安检":

java 复制代码
public String safeReply(String raw) {
    // 1. 正则/规则脱敏:手机号、身份证、银行卡
    String masked = maskSensitive(raw);
    // 2. 权限过滤:用户无权查看的字段直接替换为"权限不足"
    if (!user.hasPermission("seeSalary")) {
        masked = masked.replaceAll("(?<=收入:)[\\d,.]+元", "***");
    }
    // 3. 可选:让 LLM 复审一遍输出是否含敏感信息
    return masked;
}

4.6 防资源耗尽:限流 + 循环熔断

Agent 跑起来可能自己陷入死循环(无限调工具)。加熔断器和令牌桶:

java 复制代码
@Component
public class AgentGuard {
    private final RateLimiter perUserLimiter;   // 令牌桶
    private final AtomicInteger toolCallCount = new AtomicInteger();
    private static final int MAX_TOOL_CALLS_PER_TASK = 20; // 单任务上限

    public boolean tryAcquire(String userId) {
        // 单用户限流
        if (!perUserLimiter.tryAcquire(userId)) return false;
        // 单任务工具调用上限
        if (toolCallCount.incrementAndGet() > MAX_TOOL_CALLS_PER_TASK) {
            throw new AgentRunawayException("工具调用超限,已熔断");
        }
        return true;
    }
}

4.7 记忆安全:Agent 的"记忆"要隔离、校验、可清除

长期记忆被污染是隐蔽攻击。原则:

  • 隔离:每个用户的记忆独立存储,不共享
  • 校验:写入记忆前校验格式、敏感信息、注入特征
  • 可清除:用户有权一键清空自己的记忆(合规要求)
java 复制代码
// 写入记忆前的"安检门"
public void saveMemory(String userId, String memory) {
    if (containsInjectionPattern(memory)) {
        auditLog.warn("记忆写入疑似注入", userId);
        memory = sanitize(memory);
    }
    if (containsSensitive(memory)) {
        throw new MemoryRejectedException("记忆含敏感信息,禁止写入");
    }
    memoryStore.save(userId, memory);
}

五、完整零信任网关:把上面全部串起来

一个生产级的 Agent 请求流程:

arduino 复制代码
用户输入
   │
   ▼
┌─────────────────────────────────────────────┐
│ 1. 输入消毒:分隔符隔离、控制字符清洗          │
│ 2. 意图识别:先判"用户想干什么"               │
│ 3. 策略引擎:工具白名单 + 参数校验 + 危险动作   │
│ 4. 权限校验:数字身份 + 最小权限              │
│ 5. 证据分级:检索文档可信度过滤               │
│ 6. 执行沙箱:工具隔离执行,审计全程记录        │
│ 7. 输出安检:敏感信息过滤 + 内容复审           │
│ 8. 熔断限流:资源耗尽保护                     │
└─────────────────────────────────────────────┘
   │
   ▼
工具执行 / 人工审批通道
java 复制代码
public String guardedChat(String userId, String rawInput) {
    // 1. 输入消毒
    String clean = sanitizeInput(rawInput);
    // 2. 意图识别(低置信直接拒绝)
    Intent intent = recognizeIntent(clean);
    // 3. 策略检查(工具+参数+危险动作)
    if (!policyEngine.check(intent.toolName(), intent.args())) {
        return "该操作被策略拦截,如需执行请联系管理员审批";
    }
    // 4. 执行 + 审计
    ToolResult result = toolExecutor.execute(intent, identity);
    // 5. 输出安检
    return outputFilter.sanitize(result.toString(), identity);
}

六、零信任不是"加安全",而是架构方式

2026 年的安全共识已经转向:

传统安全 零信任安全
内网可信,外网不可信 内网外网都不可信
一次认证,长期信任 每次调用都要验证
用户权限复用 Agent 用独立数字身份
事后审计 事前拦截 + 实时检测
攻防对抗 纵深防御 + 可验证

对开发者来说,最实用的一句话建议:把你的 Agent 当成一个"未知数量的高危权限持有者"来设计------所有工具入口都要有认证、授权、参数校验、危险动作拦截和全程审计,而不是默认"模型很聪明不会乱来"。

七、系列总结(收官)

至此,Agent 前沿热点系列收官。回看这四篇,其实是一条完整的 Agent 落地链路:

arduino 复制代码
第1篇 MCP 协议    ──▶ 让 Agent 能"够得着"工具
第2篇 A2A 协议    ──▶ 让 Agent 能"对话"协作
第3篇 Context    ──▶ 让 Agent 有"好用的脑子"
第4篇 零信任安全  ──▶ 让 Agent 能"安全地干活"

前 13 篇基础系列讲"Agent 是什么、怎么搭",实战 2 篇讲"我真实怎么用",前沿热点 4 篇讲"2026 年最热的工程话题"。从理解、到使用、到前沿,这条技术路径走完了。

Agent 已经是 2026 年最重要的工程话题之一。愿你手里的 Agent 不仅强大,而且可控。

相关推荐
麻瓜pro1 小时前
DeepSeek Harness远程访问
agent
三雒2 小时前
拆解桌面Agent:WorkBuddy 删除保护机制
agent·ai编程
鱼饼Y2 小时前
DeepSeek Harness 来了!从用户界面分析DSH
agent·deepseek
RebornL2 小时前
DeepSeek Harness (DSH) 插件机制解析:一切皆插件的 Agent 运行时
agent
用户9983834541132 小时前
给 Agent 加一个「挑刺的审稿人」——Critic 与自纠错回环
agent
用户9983834541132 小时前
用LLM + Neo4j 给生物医学文献建知识图谱
agent
用户9983834541132 小时前
从研究到可交付产物——报告生成、导出与容器化部署
agent
Lear2 小时前
MinerU:把文档变成大模型能"读"的样子
agent
武子康2 小时前
GPT-Live 分析研究:从回合式语音到连续交互循环
人工智能·llm·agent