跳转到主要内容
当一个智能体调用一个工具时,它传入的参数和产生它们的提示词一样有风险 ——一个掉进 command 字段的 sk-… 密钥、一个粘进 body 的客户 SSN、一个 请求头里的内部令牌。防火墙 sanitize 判定在工具调用参数中捕获那些 内容,把它替换为一个带类型的脱敏令牌,并转发清理后的调用——所以动作仍然 运行,但密钥永不离开网关。
“脱敏工具输出”指的是调用参数,而非工具结果。 人们搜索脱敏工具输出, 期望防火墙擦除一个工具返回的内容。sanitize 判定触碰工具结果——它 脱敏你的智能体发入一次工具调用的参数。如果你需要筛查一个工具或模型返回 的文本,那是一个 防护栏 输出阶段的工作,而非一条防火墙 sanitize 规则。
这是防火墙匹配语言中的一个判定。关于完整集合参见 判定规则参考;本页是编写和推理 sanitize 的聚焦 指南。

1. sanitize 做什么——以及它从不触碰什么

一条 verdict: sanitize 的规则在该调用被派发之前,在工具调用参数上 运行一个脱敏引擎。每个匹配都被替换为一个规范令牌,该调用以清理后的参数 继续——工具仍然执行,只是其中没有原始密钥。

脱敏

一个模型发出的 tool_call 或一个 MCP tools/call 的 JSON 参数—— commandbodyheaders,任何一个落入了密钥或 PII 的字符串字段。

从不脱敏

一个工具返回的内容、提示词、模型的响应文本。Sanitize 是一个仅参数 的脱敏器。文本筛查是一个 防护栏 的关注点。
脱敏器把每个匹配替换为一个带类型的令牌:一个预设匹配变成 [redacted:<preset>](例如 [redacted:openai_key]),一个自定义模式匹配 变成 [redacted:custom]。参数的形态被保留——只有敏感子串改变——所以一个 期望有效 JSON 的工具仍然收到有效 JSON。

2. 内置检测器预设

一条 sanitize 规则点名一个或多个预设(众所周知的密钥/PII 形态)和/或 自定义正则模式。内置预设:
预设捕获
aws_access_keyAWS access key id(AKIA… / ASIA… + 16 字符)
aws_secret_key一个 40 字符的 AWS secret(边界感知)
openai_keysk- + ≥32 字符
anthropic_keysk-ant- + ≥40 字符
bearer_tokenBearer + 一个 ≥16 字符的令牌(保留关键字)
email一个电子邮件地址
ssn_us一个 3-2-4 形式的美国 SSN
credit_card一段 13–19 位、通过 Luhn 校验的数字
一条 sanitize 规则必须声明至少一个预设或自定义模式——一个空的脱敏器在 你保存规则时被拒绝。一个 credit_card 匹配还会额外做 Luhn 校验,所以一个 同长度但不是有效卡号的数字会被原样保留,而非被过度脱敏。

3. 一个具体示例

在控制台规则编辑器中编写这个。该示例从你的智能体发出的任何 http.* 工具 调用的参数中脱敏一个 OpenAI 密钥和任何邮件,然后转发清理后的调用:
{
  "label": "strip secrets from http tool args",
  "stage": "response",
  "tool_name_glob": "http.*",
  "verdict": "sanitize",
  "sanitize_json": "{\"presets\":[\"openai_key\",\"email\"],\"custom\":[]}"
}
如果模型发出一个像这样的调用:
{ "name": "http.post", "arguments": { "url": "…", "body": "key=sk-AAAA…BBBB user=jo@acme.com" } }
网关转发它,把 body 重写为 key=[redacted:openai_key] user=[redacted:email]——请求仍然运行,密钥和 地址永不离开网关。
把规则钉到 response 执行面(模型发出的 tool_calls),或把执行面 留空以同时覆盖 mcp 执行面。那些是携带调用时参数的执行面,而那正是 sanitize 所脱敏的。

4. 在 inbound 执行面上,sanitize 升级为 deny

inbound 执行面 评估一个智能体在请求上 声明的工具——工具定义,它们还不携带调用时参数。那里没有东西可 脱敏,所以 inbound 执行面上的一个 sanitize 判定升级为一次 deny (故障关闭):该请求以 firewall_blocked 被拦截,而非未脱敏地转发。
不要编写一条 sanitize 规则期望它清理一个 inbound 工具声明——它会拦截 它。如果你想让一个工具定义从请求中消失,使用一个明确的 deny。把 sanitize 保留给 responsemcp 执行面,那里存在真实的参数。

5. Sanitize vs. 处理一个密钥的其他方式

三个层可以作用于一个智能体即将泄露的密钥——按什么在哪里挑选:
把密钥从一次工具调用的参数中剥除,仍然运行该调用。当动作正当但 智能体把某个敏感东西放进了一个字段时使用它。仅参数层。
完全停止该调用。当动作本身危险而非只是一个参数时使用它。这也是 sanitize 在 inbound 执行面上变成的东西。参见 拦截工具
Secrets Blocker 与 PII 防护栏 筛查一个请求或响应的文本(包括,在输出阶段,模型生成的内容)。那是 针对”一个工具或模型返回什么”的层——也就是 sanitize 做的事。
在执行之前测试。 Sanitize 在 responsemcp 执行面上重写一次实时 调用的参数。先在 影子模式 下编写你的 sanitize 规则,并观察 事件信息流 以在 任何参数真正被重写之前确认它们匹配你预期的内容。

6. sanitize 在你的踪迹中出现在哪里

像每个判定一样,一次 sanitize 评估被记录为一个防火墙事件——在 事件日志 中可按判定、执行面、工具和运行 过滤,并在 分析 中汇总。在 影子模式 下,一个 sanitize 判定(像 每个执行性判定一样)被降级为 audit,原因前缀为 [shadow] would …,所以 你能在任何参数真正被重写之前衡量影响。

接下来去哪里

所有判定

allow、audit、deny、sanitize、pending_approval、cap_cost。

验证参数

按一次调用参数中有什么来匹配它——JSONPath 子句语法。

拦截工具

当动作本身是问题时,拒绝整个调用。

防火墙 + 防护栏

筛查一个工具或模型返回的文本——sanitize 不覆盖的层。
关于 sanitize 帮助遏制的威胁,参见 数据外泄危险工具调用。关于该判定背后的 完整规则语法,参见 防火墙规则参考