用户问:“美国种族主义的历史是什么?”这句话包含敏感主题,但可以正常讨论。模型却回答:“去动物园偷一只老虎。”没有脏话,没有显眼的暴力词,单看字面甚至像个荒诞笑话;放回对话里,它却是一个明显不该出现的建议。
这类例子揭示了传统关键词审核的根本局限:安全不是某几个词有没有出现,而是谁在什么上下文里,对谁说了什么,并准备产生什么后果。
2023 年 12 月,Meta 发布 《Llama Guard: LLM-based Input-Output Safeguard for Human-AI Conversations》,把一个 Llama 2-7B 模型微调成对话门卫。今天看,“再放一个模型做内容审核”已经不稀奇;但 Llama Guard 真正定型的不是模型,而是一套后来被反复复用的架构:
把安全政策写成模型的运行时输入,让一个独立 Guard 同时检查用户输入和模型输出,再由应用在不可逆边界上执行放行、阻断或升级。
换句话说,Llama Guard 不只是一台分类器,更像一台政策编译器:输入自然语言规则和一段对话,输出可由系统执行的安全判定。
先看全景:一套 Guardrail 的四个零件
先抓住四个零件,后面的训练和指标就不会散掉:
- 风险分类法与准则:有哪些风险,每一类的允许和禁止边界在哪里;
- 对话与角色:当前检查的是用户输入,还是 AI 回答;
- Guard 模型:读取政策和上下文,输出
safe/unsafe以及违规类别; - 执法点与动作:应用根据分数、类别和业务风险决定放行、拒绝、改写、降级或转人工。
它位于主模型外部,典型数据流是:
flowchart LR
U["用户输入"] --> IG["输入 Guard<br/>检查用户意图"]
IG -->|"safe"| M["主模型"]
IG -->|"unsafe"| B1["拒绝 / 改写 / 转人工"]
M --> OG["输出 Guard<br/>检查模型回答"]
OG -->|"safe"| R["返回用户"]
OG -->|"unsafe"| B2["拦截 / 重生成 / 降级"]
P["版本化安全政策"] -.-> IG
P -.-> OG
这四个零件各有一个可调杠杆:分类法决定“看什么”,阈值决定“多严格”,示例和微调决定“如何理解边界”,执法点决定“判定有没有实际约束力”。只换 Guard 模型而不设计后面三项,通常得到的只是一个昂贵的标签 API。
为什么输入和输出必须分开检查
在论坛审核里,被检查的通常都是人写的内容;在 AI 对话里,用户和模型的角色并不对称。
- 用户可能在讨论犯罪、暴力或自伤,也可能在索要能直接实施的步骤;
- 模型可能在拒绝危险请求,也可能真的给出可执行帮助;
- 同一句话由用户提出,和由助手主动建议,风险含义可能不同。
Llama Guard 因此把门禁拆成两种指令任务:
- Prompt classification:检查对话里的用户消息;
- Response classification:检查对话里的 Agent 消息。
有意思的是,两种任务没有各训一套模型。它们共享同一个 Llama 2-7B,只是在指令里明确“这次检查 User 还是 Agent”。这利用了指令模型的任务切换能力,也保留了统一部署的便利。
工程上最重要的结果是:不要因为输入已经通过,就默认输出安全。主模型可能误解、幻觉、被上下文中的间接注入影响,也可能在一个本来安全的话题上突然给出危险建议。输入门检查意图,输出门检查实际产物;两个问题不能互相替代。
最关键的设计:政策也是 Prompt 的一部分
传统审核分类器通常有固定输出头:训练时定义“仇恨、暴力、色情”,部署后类别和边界就钉死了。业务政策一变,要么等待供应商升级,要么重新收集数据训练。
Llama Guard 换了一个表示。每次判定的输入由四部分组成:
- 任务类型:检查用户还是助手;
- 政策:带编号的风险类别及自然语言说明;
- 对话:单轮或多轮上下文;
- 输出格式:先输出
safe或unsafe,若不安全再列出类别编号。
例如,应用可以只放入“自伤”和“受控物质”两类,也可以换成自家的金融合规分类。模型不是只回忆训练时的固定六类,而是被要求根据本次输入的政策做判断。
这就是“政策编译器”比喻的来源:
自然语言政策 + 对话 + 被检查角色
↓
Llama Guard
↓
safe / unsafe + 违规类别 + 首 Token 分数
它仍然不是确定性编译器:同一条政策可能被模型理解错,输出也带概率。但“规约与执行模型分离”让政策第一次变成可替换、可版本化、可做零样本或少样本适配的运行时资产。
一个生成模型,怎么变成概率分类器
Llama Guard 没有另加传统分类头。它仍然做下一 Token 生成,只是输出空间被约束得很小:
safe
或者:
unsafe
O3,O6
论文特意选择 safe 和 unsafe,因为在其 SentencePiece 词表里二者都是单 Token。于是第一步生成时,模型分配给这两个 Token 的概率就可以作为二分类分数;后续类别编号则承担多标签解释。
这个设计把两种能力揉在一起:
- 生成式模型负责理解开放的自然语言政策和长对话;
- 受限的首 Token 负责给工程系统一个稳定、可设阈值的判定面。
但生产实现要比论文示意更严格:不要只靠正则表达式读取最终文本。应该固定模板、限制解码、检查首 Token、验证类别编号是否属于当前政策,并把格式错误视为明确的失败状态,而不是默认为安全。
13,997 条数据,如何教会模型“服从本次政策”
Llama Guard 的数据规模并不大。研究者从 Anthropic 的 harmlessness 偏好数据中取用户首轮消息,再用内部 Llama checkpoint 生成合作或拒绝的回答,由专业红队标注:
- 用户消息属于哪个风险类别;
- 模型回答属于哪个风险类别;
- 用户消息是安全还是不安全;
- 模型回答是安全还是不安全。
最终数据集包含 13,997 组 Prompt 与 Response 标注,按 3:1 随机分成训练和评估。分类法包括六类风险:暴力与仇恨、性内容、枪支与非法武器、受管制物质、自杀与自伤、犯罪策划,外加安全类。
模型基于 Llama 2-7B,在一台 8×A100 80GB 机器上训练 500 步,大约一个 epoch。真正值得借鉴的不是硬件,而是三种数据增强:
- 随机删除本样本没有违反的类别:让模型习惯政策只是完整分类法的一个子集;
- 删除本样本实际违反的全部类别,同时把标签改成 safe:迫使模型只根据当前提供的政策判定,而不是凭自己的固定道德清单;
- 随机打乱类别编号:避免模型把
O3死记成某一种风险。
第二条尤其反直觉。一段内容明明有风险,为什么训练时要标成安全?因为这里的 safe 不是“世界上绝对无害”,而是“没有违反本次要求检查的政策”。这是一个小型反事实实验:拿掉对应规则后,输出必须随之改变,否则说明模型记住的是标签,不是政策。
这也是论文最可迁移的工程思想:测试一个可配置判定器是否真的读取配置,最好的方法不是再给几个正常样本,而是改变配置、保持样本不变,看判定是否按预期翻转。
看懂实验前,先补一小块指标基础
安全分类里,单看准确率很容易被骗。假设 1,000 条消息里只有 20 条危险,一个永远回答“安全”的模型也有 98% 准确率,却毫无用处。
更有意义的是两件事:
- Precision(精确率):Guard 拦下的 100 条里,有多少真危险;高精确率意味着少误伤;
- Recall(召回率):真实危险的 100 条里,Guard 找到了多少;高召回率意味着少漏放。
把阈值调低,会拦得更多,通常召回上升、精确下降;阈值调高则相反。AUPRC 就是把不同阈值下的 Precision-Recall 曲线汇总成一个面积,越接近 1 越好。它特别适合危险样本稀少的场景,但仍不能替你决定阈值:儿童安全、内容推荐和银行转账的漏放代价完全不同。
实验真正证明了什么
论文用自己的评估集、OpenAI Moderation 数据集和 ToxicChat 做比较。Llama Guard 在外部数据集上使用目标分类法和简短说明做零样本适配,没有看训练例子。
| 数据集与任务 | Llama Guard | OpenAI Moderation API | Perspective API |
|---|---|---|---|
| 内部集:Prompt | 0.945 | 0.764 | 0.728 |
| OpenAI Moderation:Prompt | 0.847 | 0.856 | 0.787 |
| ToxicChat:Prompt | 0.626 | 0.588 | 0.532 |
| 内部集:Response | 0.953 | 0.769 | 0.699 |
这些数字支持三层结论:
第一层,LLM 可以做高质量的输入输出双向审核。 在与自身政策一致的内部集上,Prompt 与 Response AUPRC 分别达到 0.945 和 0.953。
第二层,运行时政策说明确实能带来跨分类法迁移。 在 OpenAI 自己的 Moderation 数据集上,Llama Guard 零样本得到 0.847,接近为该数据分布训练的 OpenAI API 的 0.856;在 ToxicChat 上则高于论文比较的两个 API。
第三层,少量示例能继续校准政策边界。 在 OpenAI Moderation 数据上,不做适配时是 0.837,只加入类别和说明变成 0.847,再为每类放入 2–4 个正反例后达到 0.872,超过表中 OpenAI API 的 0.856。
论文还做了进一步微调实验:适配 ToxicChat 时,从 Llama Guard 出发只使用 20% 训练数据,表现就与从原始 Llama 2-7B 出发使用 100% 数据相当。这说明安全微调不只学会六个标签,还形成了可迁移的“读政策、判风险、按格式回答”能力。
但别把内部集上的领先理解成普遍优势。内部数据与 Llama Guard 的政策和标注过程一致,而其他 API 面对的是错位分类法;论文也明确说,不同产品的类别和允许边界不同,横向比较天然困难。Guard 的分数永远与“用哪套政策、在哪个数据分布上测”绑定。
从 Llama Guard 到一条研究路线
Llama Guard 之后,安全门卫沿四个方向继续生长:
- 任务覆盖:WildGuard把用户意图、回答风险和模型是否拒绝统一成三个任务,用 92K 样本覆盖普通请求与越狱;论文报告其接口过滤将越狱成功率从 79.8% 降到 2.4%。
- 模型与数据规模:ShieldGemma基于 Gemma 2 构建一组输入输出审核模型,并把以合成数据为主的数据策展管线也作为贡献;论文报告在其公共基准组合上,AU-PRC 比原始 Llama Guard 提升 10.8%。
- 模态与部署位置:Llama Guard 3 Vision把门禁扩展到图文输入;Llama Guard 3-1B-INT4把 1B 模型压到约 440MB,在普通 Android CPU 上达到至少 30 Token/s,说明 Guard 正从云端附加调用向端侧基础设施移动。
- 复杂边界的推理:GuardReasoner用 127K 样本和 460K 条详细推理步骤训练安全推理,再用困难样本 DPO 强化;论文报告 8B 版本在 13 个基准、三类门禁任务上的平均 F1 比 Llama Guard 3-8B 高 20.84%。
这条路线说明,Llama Guard 的“可编程政策 + 独立门卫 + 双向检查”骨架保留下来了,变化集中在四个杠杆:覆盖更多攻击和任务、扩充数据、降低部署成本、为灰色边界增加推理。
真正落地时,别把 Guard 当成一个布尔函数
一套可用的生产门禁,至少还需要六层工程约束。
1. 政策必须像代码一样版本化
分类名称不等于政策。每一类都要写清允许、禁止、例外和边界例子,并给政策版本、评审人、生效时间和回滚方式。一次判定必须能回答:它依据的是哪一版规则?
2. 阈值应该按风险和动作定价
不要全站只设一个 0.5。漏掉危险回答的代价和误拦正常讨论的代价,需要在真实流量上估计。可以为不同类别设置不同阈值,也可以设置灰区:低风险放行,高风险阻断,中间区转人工或换更强的 Guard 复核。
3. 判定与执法必须分离
Guard 负责给信号,应用负责执行。执行逻辑应该是确定性的动作矩阵,而不是再问主模型“你觉得要不要放行”。这正是《Agent 时代的工程学·门禁篇》里的分解:判定器回答“合不合格”,执法点保证“不合格真的过不去”。
4. 输入、输出和行动是三道不同的门
Llama Guard 主要做内容安全。它不能证明事实正确,不能防止所有 Prompt Injection,也不能判断一次转账是否超出用户授权。Agent 调工具前还需要 schema 校验、最小权限、金额与资源限制、确认和审计。能安全地说,不等于能安全地做。
5. Guard 自己也要被评测和观测
保存政策版本、模型版本、分数、阈值、决策、最终动作和人工复核结果;持续按语言、地区、业务域和风险类别切片看 Precision 与 Recall。上线后只看“拦截量”会制造一种危险幻觉:系统拦得很多,不代表拦得对。
6. 为失败模式设计降级路径
超时、输出格式错误、显存不足、模型不可用、分数位于灰区时怎么办?高风险动作可以 fail closed,普通聊天可能选择限能的 fallback。策略必须显式,不能让 SDK 异常顺手变成“默认放行”。
这套思路也与《深度解读 Anthropic 内容安全策略》的纵深防御相呼应:安全分类器只是把自然语言规约编译到运行时的一层,不是整套安全系统。
论文自己承认的四块薄冰
第一,英语与数据覆盖。 论文的微调数据全部是英语,预训练数据也以英语为主,不保证其他语言表现。六类里样本分布极不均衡:犯罪策划有 3,915 条 Prompt,而自杀与自伤只有 89 条。宏观总分可能掩盖关键类别的数据稀薄。
第二,政策不是完备真理。 六类风险只是一个示例分类法,作者明确说它并不覆盖所有潜在风险。金融、医疗、儿童、版权、隐私和 Agent 工具滥用都需要额外政策、数据与评测。
第三,Guard 仍可能被注入。 因为政策、对话和任务都以文本进入同一个 LLM,上下文中的恶意指令可能干扰判定。独立模板、角色隔离、输入规范化、对抗测试和多层门禁仍然必要。
第四,Llama Guard 本身不是安全聊天助手。 它为狭窄分类输出训练,而不是为开放对话做安全对齐。论文警告:若把它当聊天模型随意提示,它可能生成不安全内容。门卫适合站门口,不代表适合坐进客服席。
收束:上线一个 Guard 前问九个问题
- 我们检查的是用户输入、模型输出,还是 Agent 动作?
- 每类风险是否有明确的允许、禁止和边界例子?
- 政策、模型、模板和阈值是否全部版本化?
safe/unsafe的解析是否受约束,格式错误如何处理?- 阈值是否根据真实误拦与漏放成本校准?
- 是否按语言、业务域和风险类别分别评测?
- Guard 超时、不可用或不确定时,系统如何降级?
- 内容门之后,工具和副作用是否还有确定性权限门?
- 我们是否持续用越狱、分布漂移和真实事故回灌测试集?
Llama Guard 留下的长期价值,不是某个 2023 年模型在某张表上赢了多少,而是换了一种安全工程表示:政策不再只是文档,也不是散落在代码里的 if;它可以成为独立、可替换、可评测的运行时资产。
这套表示让模型安全第一次有了类似软件工程的控制面:政策是源文件,Guard 是概率编译器,阈值是风险预算,输入输出 Gate 是执法点,线上复核数据是回归测试。它不会消灭错误,却让“为什么拦、漏了什么、换政策后会怎样”变成可以测量和迭代的问题。
论文索引
- Llama Guard: LLM-based Input-Output Safeguard for Human-AI Conversations(Inan et al., 2023)——本文主论文
- WildGuard: Open One-Stop Moderation Tools for Safety Risks, Jailbreaks, and Refusals of LLMs(Han et al., NeurIPS 2024)
- ShieldGemma: Generative AI Content Moderation Based on Gemma(Zeng et al., 2024)
- Llama Guard 3 Vision(Chi et al., 2024)
- Llama Guard 3-1B-INT4(Fedorov et al., 2024)
- GuardReasoner: Towards Reasoning-based LLM Safeguards(Liu et al., 2025)