# AI 面试产品交付：从练习工具到可审计系统

> 证据基线：2026-09-07。DeepInterview 固定 HEAD 为 `241799b39e781737ccec30157d8201bcc572064c`，GrillKit 固定 HEAD 为 `15a400afb08349ad9b73f31a0c92ba147032164c`。文中 **【事实】** 仅指两份审计或固定源码直接支持的结论；**【建议】** 是面向拟建产品的交付主张；**【未验证】** 表示虽有源码或项目自述，但审计未完成真实集成、性能或质量验证。README 只用于理解作者意图，不作为测试通过证据。

## 1. 执行摘要

**【建议】AI 面试首先是一条业务闭环，不是一个“会问答的模型”。** 它从候选人材料和岗位要求出发，把岗位拆成可观察的能力，把能力映射为有依据的题目，再通过语音、文本或代码收集证据。系统随后按预先发布的评分标尺解释证据，生成带出处、覆盖范围和不确定性的反馈。用户纠错、人工复核、申诉和线上质量数据又回到题库、评分标尺和发布流程，推动下一版改进。只有材料、能力、题目、对话、证据、评分、反馈和复盘首尾相接，产品才是可管理系统；只让模型自然地问几句话，只能证明一次演示能进行。

这条闭环直接决定产品能否经营。材料必须说明来源，题目必须说明为什么被选中，追问必须受轮次和范围约束，分数必须指向回答或测试结果，技术故障必须与能力不足分开，旧报告必须能还原当时使用的题库、模型和规则。这样，团队才能回答三个基本问题：这次结果依据什么；如果错了，影响到谁；修复后怎样恢复而不改写历史。第一版因此应先交付“可重复、可解释、出错后可恢复的练习与反馈链路”，再逐步增加语音、检索、代码执行和更高风险用途。

**【事实】** DeepInterview 是以实时语音为主要交互方式的模拟面试系统。固定源码覆盖网页体验、简历与职位描述解析、公司信息检索、问题规划、实时对话、逐字稿、结构化评分、报告和数据保存，并非单纯的界面样机；但真实媒体、语音识别与合成、模型、完整知识检索、云端数据库和对象存储并未在本次审计中完成端到端运行。报告页在若干尚未就绪的状态使用样例评分卡，所以页面可显示不能证明真实面试评分成功（[DeepInterview 审计](ai-interview-research/evidence/deepinterview-audit.md)，[报告页源码](ai-interview-research/repos/DeepInterview/apps/web/app/report/[id]/page.tsx)）。

**【事实】** GrillKit 是单用户、本地优先的技术面试训练器。固定源码覆盖理论题、编码题、组合会话、计时、最多两轮追问、结构化 AI 评价、本地数据库、离线语音和可选的隔离代码执行。它定义了候选人可见的公开测试、仅服务端可见的隐藏测试及相应执行流程；但固定题库中 44/44 道编码题均为 AI 模式，测试执行模式、公开测试和隐藏测试的数量都为 0。因此项目说明中的“运行公开测试、提交后运行隐藏测试”是能力描述，不是当前题库已验证的体验（[GrillKit 审计](ai-interview-research/evidence/grillkit-audit.md)，[task spec](ai-interview-research/repos/grillkit/app/coding/domain/task_spec.py)，[run tests](ai-interview-research/repos/grillkit/app/coding/use_cases/run_tests.py)）。

**【建议】** 第一版应定位为候选人自主练习与形成性反馈工具，而非自动录用、淘汰、排名或远程监考系统。应组合 DeepInterview 的上下文准备和语音闭环，与 GrillKit 的确定性状态机、题目快照和代码执行边界；不应照搬两者的默认信任网络、未校准模型分数或不完整数据治理。招聘评估必须作为独立高风险产品线重新完成岗位效度、法律审查、公平性校准、人工复核和申诉机制。产品明确排除真实面试中的隐蔽监听、实时提词、代答、伪造身份和规避监考。

<!-- EARLY-GUIDE-START -->

## A. 一场 AI 面试如何真正完成

**结论：一场面试真正完成，不是页面出现“已结束”，而是每个结论都能沿着材料、计划、回答和评分一路查回去。** 以下用一个贯穿案例解释建议流程。人物、岗位、回答和数值均为示例，不代表两个参考项目已经实现或达到相同质量；引用的工程切片则来自固定源码与两份审计。

<div class="journey-strip" role="list" aria-label="AI 面试业务闭环">
  <div class="journey-step" role="listitem"><svg aria-hidden="true"><use href="#i-file"></use></svg><span>01</span><strong>读材料</strong><small>保留简历/职位描述出处</small></div>
  <div class="journey-step" role="listitem"><svg aria-hidden="true"><use href="#i-score"></use></svg><span>02</span><strong>定能力</strong><small>写成可观察信号</small></div>
  <div class="journey-step" role="listitem"><svg aria-hidden="true"><use href="#i-code"></use></svg><span>03</span><strong>选题目</strong><small>冻结题目与标尺</small></div>
  <div class="journey-step" role="listitem"><svg aria-hidden="true"><use href="#i-mic"></use></svg><span>04</span><strong>收回答</strong><small>语音、文本与代码</small></div>
  <div class="journey-step" role="listitem"><svg aria-hidden="true"><use href="#i-eye"></use></svg><span>05</span><strong>固证据</strong><small>确认转写与测试</small></div>
  <div class="journey-step" role="listitem"><svg aria-hidden="true"><use href="#i-scale"></use></svg><span>06</span><strong>做评分</strong><small>规则校验模型判断</small></div>
  <div class="journey-step" role="listitem"><svg aria-hidden="true"><use href="#i-roadmap"></use></svg><span>07</span><strong>再改进</strong><small>复核申诉回到发布</small></div>
</div>

候选人林晨申请“中级后端工程师”。他的简历（CV）写到自己负责过订单服务，使用消息队列处理异步任务；职位描述（JD）要求能够设计高并发服务、排查线上故障，并解释数据一致性的取舍。系统不应从这两份材料直接跳到“给林晨打分”。CV 是候选人的自述，JD 是岗位要求，两者都不是已经证明的能力。系统要先把它们变成一份可检查、可冻结的面试计划。

### A.1 从材料到能力：先确认要测什么

**结论：材料解析的产物不是候选人画像，而是带出处的待验证假设。** 系统分别读取 CV 和 JD，保留原文位置、解析版本和内容指纹（用于确认内容没有被替换的哈希值）。它从 JD 提取岗位目标、级别、必备能力和限制条件，再从 CV 提取经历、项目、时间和候选人声称使用过的技术。随后形成三项待测能力：并发与容量设计、故障诊断、数据一致性。

每项能力还要写成“可观察信号”。这意味着系统不评价“聪明”“有潜力”之类模糊标签，而是说明要在回答中看到什么。例如，并发与容量设计可以观察是否给出流量假设、瓶颈、保护顺序和验证方法；故障诊断可以观察是否从现象提出假设，再用指标或日志排除；数据一致性可以观察是否识别失败边界、补偿办法和用户影响。

**为什么需要。** 如果没有能力模型，选题只能依赖关键词相似或模型即兴判断。CV 里出现“Kafka”可能只是参与过项目，不能自动证明候选人理解消息可靠性；JD 里出现“沟通能力”也不能授权系统用口音或语速评分。带出处的能力项把“岗位需要什么”和“候选人已经证明什么”分开。

**失败会怎样。** 扫描版 CV 可能解析为空，JD 可能缺少级别，技能同义词可能被漏掉，模型也可能把自述当事实。**【建议】** 输入不完整时停在“需要补充材料”，说明缺什么；不允许为了维持流程而自动补全岗位要求。无法从材料支持的推断要标为“待确认”，不能进入正式评分。

**【事实】** DeepInterview 的准备流程会并行处理 CV、JD 和公司资料，再做差距匹配与问题规划；其结构化对象包括候选人、岗位、差距、计划问题和面试上下文。这为“先结构化、再匹配、后规划”提供了源码依据，但复杂版式、多语言和真实岗位上的抽取准确率仍属 **【未验证】**（[DeepInterview Prep 审计](ai-interview-research/evidence/deepinterview-audit.md#51-prep)，[准备流程源码](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/prep/graph.py)）。

### A.2 从能力到题目：把有限时间花在关键证据上

**结论：题目规划不是让模型自由出题，而是在已发布题库中做受约束选择。** 系统为三项能力选择主问题、评分标尺和允许的追问范围，并记录每题的选择理由。

| 系统先确认什么 | 本场怎样选择 | 回答中要看到什么 | 失败时立即做什么 |
|---|---|---|---|
| 并发与容量设计 | “订单流量增长十倍，你会先估算和保护哪些环节？” | 容量假设、简单计算、瓶颈、限流与降级顺序 | 若题目难度不匹配级别，停止发布该题并回到上一版本 |
| 故障诊断 | “消费积压但数据库负载正常，你会怎样定位？” | 排查顺序、可验证假设、指标和依赖关系 | 若问题与 JD 无关，标记计划缺陷，不把回答差异算到候选人 |
| 数据一致性 | “库存扣减和订单创建不能同时成功时，你怎样取舍？” | 失败场景、幂等、补偿、一致性边界和用户影响 | 若评分标尺与题目不配套，该题不能进入正式会话 |

“评分标尺（rubric）”是把“答得好”拆成不同等级的可观察标准、示例和反例。题目开始前，系统发布“计划快照”：把题目修订、rubric、语言、允许追问次数、材料版本和模型策略固定下来。之后题库即使更新，这场面试仍按原快照解释。

**为什么需要。** 固定主问题保证不同场次有共同基线；受约束追问允许澄清回答，却不能临时改变考试范围。计划快照还能解释为什么两个候选人收到不同问题，以及差异是否来自岗位相关信息。

**失败会怎样。** 自由生成问题会出现难度漂移、重复覆盖、遗漏关键能力或泄露不当内容。旧题被覆盖后，历史报告还可能按新 rubric 解释，造成同一答案“今天三分、下月四分”却找不到原因。**【建议】** 题库采用不可变修订；会话保存题目和 rubric 快照；动态追问只补充原能力证据，并受次数、时长与禁区约束。

**【事实】** GrillKit 会在创建会话时快照题目、rubric、代码和任务规格，历史结果不必依赖当前题库；会话阶段和追问深度由领域规则控制，而不是由模型随意推进（[GrillKit 数据模型](ai-interview-research/evidence/grillkit-audit.md#7-数据模型与迁移)，[会话阶段源码](ai-interview-research/repos/grillkit/app/interview/domain/session_phases.py)）。

### A.3 从提问到回答：实时系统的任务是收集证据

**结论：实时对话可以自然，但被保存和评分的事实必须稳定。** 林晨进入面试后，系统读出第一题。他先回答：“我们会先扩容，再看数据库。”语音识别（STT，把声音转换为文字的服务）持续显示临时转写。临时文字会随着后续音频修正，只供即时反馈；只有一轮结束并通过检查后，才生成“已确认回答”。

系统发现回答没有容量假设，于是在原题范围内追问：“你会用哪些数据估算扩多少？扩容失败时先保护什么？”林晨补充峰值订单量、单实例吞吐、队列积压阈值，并提出先限制非核心查询、保护下单写入。模型可以建议这句追问，但能否追问、最多追问几次、何时结束，由会话状态机决定。状态机可以理解为一张不允许随意跳步的流程表：系统清楚知道当前处于准备、连接、答题、评分还是完成，只有满足规则才能进入下一步。

**为什么需要。** 实时链路同时处理音频、转写、模型输出、语音播放、计时和断线重连。任何消息都可能迟到或重复。如果把临时转写直接评分，后续修正不会反映到分数；如果让模型决定“本题已完成”，同一句话在不同模型版本下可能推进到不同状态。

**失败会怎样。** 第二题回答时网络中断，浏览器重连后重新发送上一条提交。如果没有“幂等键”（同一请求重复到达也只产生一次结果的标识），系统可能保存两份答案、调用两次模型并重复计费。**【建议】** 每个提交带幂等键和预期会话版本；服务端发现已处理后返回原结果，版本不匹配则重新读取状态，不允许旧页面把第三题退回第二题。

语音不是能力本身。设备或语音服务异常时，系统应转为文本，并记录“为何降级、从何时开始、哪些回答受影响”。“降级”是高级能力不可用时保留核心任务的备用方式，例如语音合成失败后继续显示问题文本。降级状态进入报告，但不进入能力分数。

**【事实】** DeepInterview 的实时工作进程保存已确认转写，SessionGuard 限制时长和轮次，TranscriptFlusher 周期保存转写；GrillKit 的理论评价最多两轮追问。这些是可复用的恢复和边界意识，但真实设备、口音、噪声及供应商时延在本次审计中仍属 **【未验证】**（[DeepInterview Live 审计](ai-interview-research/evidence/deepinterview-audit.md#53-live)，[GrillKit 模型与语音](ai-interview-research/evidence/grillkit-audit.md#6-模型与语音)）。

### A.4 从文字和代码到证据：让确定性结果优先说话

**结论：开放式回答需要解释，代码执行需要事实，两者不能混成一个“AI 感觉”。** 理论题保存题目、已确认回答、追问、引用片段和 rubric 对应项。编码题还要保存候选人的代码版本、编译结果、公开测试、隐藏测试和资源使用。

林晨编写库存扣减函数。点击“运行”时只执行公开测试；点击“正式提交”时，服务端执行不向浏览器暴露的隐藏测试。编译是否成功、通过多少测试属于确定性信号。模型可以解释代码可读性、边界意识和取舍，却不能把测试失败改写为通过，也不能在没有测试时假装“已验证正确”。

**为什么需要。** 理论题适合观察推理过程，测试适合验证具体行为。二者组合，既避免只看输出忽略思路，也避免只听解释不验证代码。基础设施失败、候选代码失败和未运行必须是三个状态：`INFRA_ERROR`、`TEST_FAILED`、`NOT_RUN`，不能都折叠成 false。

**失败会怎样。** 隐藏测试进入浏览器会泄题；执行环境若与应用共享网络和秘密，恶意代码可能扫描内网；没有参考解与错误解的题目即使“有测试字段”也可能无效。**【建议】** 测试由服务端按题目版本装配；执行环境默认无外网、无生产密钥、限 CPU/内存/进程/输出，完成后销毁工作区；基础设施失败只触发重跑或人工处理，不产生负向能力分。

**【事实】** GrillKit 已实现公开与隐藏测试的数据结构、客户端隐藏边界以及 Run/Submit 流程；但固定题库中 44/44 道编码题全部为 AI 模式，tests 模式、public tests、hidden tests 均为 0。因此当前证据只证明判题框架存在，不能证明题库已具备真实判题体验（[GrillKit 题库与判题](ai-interview-research/evidence/grillkit-audit.md#5-题库与判题)，[任务规格源码](ai-interview-research/repos/grillkit/app/coding/domain/task_spec.py)）。

### A.5 从证据到报告：没有测到，不等于能力差

**结论：报告的核心不是总分，而是“哪项判断由哪段证据支持，哪些地方还不能判断”。** 会后系统先冻结本场输入：题目版本、已确认转写、文本修订、代码、测试结果、rubric、模型和规则版本。随后逐项评分。

以并发能力为例，报告应同时展示：候选人给出的容量假设；该片段对应 rubric 的哪一项；仍缺少什么，例如数据库与消息队列如何分别压测；规则确认了哪些事实；模型给出什么解释；证据范围有多大。覆盖率（coverage）表示计划内容中有多少取得有效证据。三项能力只完成两项时，报告应写“覆盖不足，数据一致性暂不能判断”，而不是给缺失项填零再生成完整画像。

**为什么需要。** 分数把复杂证据压缩成一个数字，很容易制造过度确定。证据、覆盖和不确定性让用户知道分数适用于哪里，也让复核者能够修改具体环节，而不是争论模型是否“聪明”。

**失败会怎样。** 如果转写修正后仍引用旧文本，或者单题评分失败却继续汇总总分，报告会显得完整但事实已经断裂。**【建议初始目标】** 100% 的分项判断至少带一个可定位回答片段或确定性测试；没有有效证据的分项 100% 显示“未覆盖”“尚未判定”或“需复核”，不得自动填低分。用户修订转写时保留原文、修改人、时间和原因，只重算受影响题，不覆盖旧报告。

**【事实】** DeepInterview 把能力名称绑定计划目标，把分数限制在 0–5，由代码派生等级；未回答题不记零分，而由 coverage 表达；单题失败也不会抹掉其他题。这些实现支持“局部可用、缺失不补零”的方向，但招聘效度和真实评分质量仍属 **【未验证】**（[DeepInterview 会后评分](ai-interview-research/evidence/deepinterview-audit.md#54-post评分与报告)，[评分源码](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/post/evaluator.py)）。

本场最终形成一条可复核链：`CV/JD 原文 → 能力项 → 题目修订 → 主问题与追问 → 已确认回答/代码 → 测试与引用 → rubric → 模型与规则版本 → 反馈 → 纠错或复核记录`。只要其中一个箭头断开，争议处理就会退化成“相信模型”或“相信截图”。

## B. 为什么 AI 会不稳定，以及系统如何变得稳定

**结论：模型不稳定，不等于系统必须不稳定。** 概率模型可能因上下文顺序、版本、参数和供应商路由给出不同表达；输入还会受材料解析、网络、语音和题库质量影响。可靠系统不要求每个组件永不失败，而是用七层保障让错误在形成不利结论前被发现、隔离和纠正。

### B.1 先理解不稳定从哪里来

输入可能失真：CV 是扫描件，JD 缺关键要求，麦克风漏字，语音识别把否定词听反。流程可能竞争：重连重复提交，两个工作进程同时追加答案，上一轮迟到的模型输出污染下一轮。模型可能波动：输出字段缺失、超时、截断、被回答中的指令干扰，或供应商静默升级。评价也可能不稳：rubric 含糊，人工评审之间尚未达成一致，小语种或特定设备的误差被总体均值掩盖。运行环境还会引入队列积压、数据库冲突、预算耗尽和迁移失败。

所以“接口返回 200”“对话很流畅”“报告成功生成”都不是充分证据。稳定至少意味着：该保存的不能丢；同一提交不能重复算；听不清时不能猜；供应商超时不能嫁祸给候选人；每项结论必须拿得出依据；高影响结果可以暂停和复核。

### B.2 七层保障怎样相互兜底

**结论：七层保障不是七份独立清单，而是前一层漏过错误时，后一层继续阻断传播。**

| 先守住哪一层 | 用什么白话机制 | 重点发现什么 | 异常后马上做什么 |
|---|---|---|---|
| 输入 | 材料、题库和音频先过安检 | 空解析、缺字段、无测试题、低置信转写、错误语言 | 停止准备、提示补充、切文本、标记证据待核对 |
| 流程 | 由规则决定现在到哪一步 | 重复提交、越过阶段、迟到消息、并发覆盖 | 返回首次结果、拒绝非法迁移、从检查点恢复 |
| 模型 | 把模型放进有字段、有版本、有超时的盒子 | 非法结构、分数越界、超时、截断、注入和版本漂移 | 有限重试、熔断、切已校准备份或转人工 |
| 证据 | 每个结论指向原话、测试和版本 | 引用丢失、旧转写、未运行测试、覆盖不足 | 撤回受影响分项，显示尚未判定，不补零 |
| 质量 | 用固定样本和人工共同标尺检查 | 重复波动、严重高低估、题目失效、群体误差 | 阻断发布、修 rubric、缩小适用范围 |
| 运行 | 用服务目标、预算和告警控制影响范围 | 队列积压、供应商故障、重试风暴、成本失控 | 停止扩量、保存事实、透明降级、列出受影响场次 |
| 治理 | 明确谁能发布、复核、撤回和申诉 | 未批准版本、高风险用途、供应商政策变化 | 暂停结果消费、人工复核、批量纠正或回滚 |

输入层先防止“坏材料进系统”。材料要有来源、类型、大小、解析结果和版本；编码题要有参考解、公开/隐藏测试和代表性错误解；关键语音片段低置信时先核对。流程层随后固定“发生了什么”。状态机只接受允许的迁移，浏览器不能自行宣告超时或完成，模型也不能直接修改会话状态。

模型层只让 AI 做受约束的语义任务。结构化输出（用固定字段传递结果的格式）要求题目 ID、rubric 项、证据位置、分数、缺失项和拒绝原因都符合契约；代码再检查分数范围、题目身份和引用边界。模型、提示词、参数、供应商和结构定义全部版本化。格式错误只允许有限修复，超时达到截止时间后熔断，不无限重试。

证据层回答“凭什么”。检索增强生成（RAG，先从获准资料找到相关片段，再让模型依据片段回答）必须返回可定位引用、内容指纹和索引版本。检索文本始终是不可信数据，不能覆盖系统指令，也不能调用未授权工具。版本冻结则确保历史报告仍使用当时的题库、rubric、模型、提示词、转写修订和测试集解释。

质量层回答“这种判断是否长期站得住”。固定质量集（golden set，一套由人认真判断过、每次升级都要重考的标准样本）覆盖岗位、级别、语言、口音、设备、回答长度、无答案和攻击输入。先确认受训评审按 rubric 能达到基本一致，再比较模型。运行层用服务等级目标（SLO，对关键用户结果设定的可靠性目标）、错误预算、熔断和故障演练控制影响范围。治理层最后决定哪个版本可以发布、哪些结果必须人工复核、申诉成立后怎样撤回和批量纠正。

这些机制互相补位。结构化输出只能保证结果形状正确，不能保证内容真实；检索引用只能说明来源，不能证明推理正确；版本冻结能解释差异，不能自动消除偏差；规则校验能拦住越界分数，不能替代人工标尺；幂等能防止重复评分，不能修复错误转写；人工复核能处理边界案例，不能代替日常自动监测。稳定来自组合，而不是押注某一个“更强模型”。

### B.3 完整异常案例：三种故障同时发生时怎样不误伤

**结论：当语音识别错误、模型超时和覆盖不足同时发生，系统的正确结果是“暂不能完整判断”，不是低分。** 假设一场后端面试计划 6 题。第三题讨论数据库事务，林晨说：“可重复读并不能完全解决幻读，具体还取决于数据库实现。”背景噪声和断流让 STT 转成“可重复读能完全解决幻读”，恰好改变了技术含义。随后评分模型连续超时；第五、六题又因会话中断没有完成。最终只有 3/6 题有回答，其中只有 2 题形成可靠评分证据。

用户首先看到的是可理解的处置，而不是内部错误码。第三题关键句被高亮为“转写可能有误，请核对或改用文字”；计时在建议允许范围内暂停；模型超时后页面显示“回答已保存，评分稍后完成”，不会出现样例分数。会话结束后，报告明确写“回答覆盖 3/6，可靠评分覆盖 2/6，证据不足，暂不生成整体等级”。前两题已经核验的反馈仍可查看。用户可以修正第三题文本、补答未完成题，或申请人工复核；平台故障造成的补答不消耗用户次数。

系统内部保留更精确的事实。原始已确认音频轮次、机器转写、置信度、丢包情况和候选人修订分别保存；修订以新版本追加，不覆盖原文。第三题先进入 `TRANSCRIPT_UNVERIFIED`，禁止负向结论提交。主模型达到截止时间后只进行一次受预算约束的短重试；再次失败记录 provider、model、deadline、错误类型和调用费用，再切换经过同一 rubric 校准的备用模型。备用仍失败时进入 `SCORING_PENDING`，不回 mock，不写零分。

覆盖率要分开计算：回答覆盖说明完成了多少题，可靠评分覆盖说明多少题取得可用评分，rubric 覆盖说明关键评价项是否都获得证据。任一覆盖低于发布门槛，就阻止总体等级、排名和录用倾向。系统同时把 `STT_LOW_CONFIDENCE`、`MODEL_TIMEOUT`、`SESSION_INTERRUPTED` 写入不可追加修改的事件记录，并通过事务 outbox（数据库提交事实时，同事务登记待发送事件的机制）通知评分队列和事故看板。

当同一语言或区域的低置信率与同一模型的超时率一起升高，运行层按能力熔断：新会话默认转文本或备用 STT，评分转异步，已开始会话保存检查点。恢复后先用探针和小流量验证，再按幂等键重放 `SCORING_PENDING`。如果用户已经修正转写，只重算第三题；前两题不重复调用、不重复收费。旧的降级报告保留为历史版本，并以“已撤回”连接到新报告，不能静默覆盖。

复盘时不把三种故障合并成“模型表现差”。输入侧检查噪声、断流和关键术语核对；模型侧检查超时、重试、备用路由和费用；流程侧补充“可靠评分覆盖不足时禁止总体结论”的契约测试；治理侧查找同版本、同语言、同区域的全部受影响场次并确认纠正。这个案例体现的是“体验尽量继续，结论必须谨慎”：服务可以柔性降级，高影响判断必须严格关闭。

### B.4 承诺什么，不承诺什么

**结论：可信承诺应描述系统怎样发现和处理错误，而不是声称 AI 永不出错。**

| 我们承诺怎样做 | 我们不承诺什么 | 用什么证明承诺兑现 |
|---|---|---|
| 每项分数都连接题目、rubric、回答片段、测试和版本 | AI 分数等于一个人的真实能力或未来绩效 | 证据记录、引用抽检、版本快照和人工复核 |
| 低 STT 置信、模型超时和基础设施失败不自动变成低分 | 所有语言、口音、噪声和设备下语音识别永不出错 | 转写核对、文本替代、错误分类和分语言质量集 |
| 覆盖不足时显示证据不足，不制造完整画像 | 每场面试一定生成完整分数、排名或录用建议 | 多层 coverage、报告发布门槛和降级状态 |
| 相同提交重复到达只产生一次业务结果 | 网络、设备和第三方服务永不失败 | 幂等键、唯一约束、对账和恢复演练 |
| 模型、题库、rubric 和提示词变更经过版本化回归 | 概率模型对同一输入永远逐字一致 | golden set、重复运行方差、发布清单和回滚记录 |
| real、mock、sample、degraded 在页面、接口、导出和分析中一致标识 | 页面能展示或 README 写明支持，就代表生产链路已验证 | 来源状态字段、数据域隔离和下游契约测试 |
| 不把口音、停顿、流畅度、摄像头或设备质量直接等同岗位能力 | AI 天然客观无偏，或一次校准永久有效 | 岗位相关 rubric、公平性切片、置信区间和申诉记录 |
| 高影响结果可以复核、纠错、撤回和恢复 | 自动评分可以替代招聘责任或成为唯一淘汰依据 | 复核时限、申诉审计、用途控制和独立 Go/No-Go |

**【事实】** DeepInterview 在缺少密钥或未知 provider 时可能使用 MockLLM，报告页在若干状态使用 sample scorecard；GrillKit 虽有 public/hidden tests 框架，但固定题库 44/44 道编码题的 tests/public/hidden 均为 0。这些事实说明 demo、README 和框架存在都不能替代真实生产验证（[DeepInterview 审计限制](ai-interview-research/evidence/deepinterview-audit.md#15-审计限制)，[GrillKit 审计限制](ai-interview-research/evidence/grillkit-audit.md#14-未完成项与限制)）。

## C. 怎样判断它是否真的靠谱并可持续经营

**结论：“靠谱”至少有四种，必须分别测量、分别处置；可持续经营还要求题库、模型、供应商、申诉和成本形成固定节奏。** 系统可用只说明用户大多能完成流程；回答质量说明问题与反馈是否有用；评分可信说明证据能否稳定映射到共同标尺；公平合规说明技术误差、数据处理和使用方式是否合理。一个维度达标不能替代另一个维度。

### C.1 四种靠谱：指标必须连接异常动作

下表所有数值均为 **【建议初始目标】**，不是两个参考项目的实测结果。P95 表示 95% 的请求应快于该值，用于观察少数用户遇到的长等待；正式阈值必须用试点、压测、校准和法律审查修订。

| 先判断什么 | 持续看哪些信号 | 越界后立即采取什么行动 | 何时允许恢复 |
|---|---|---|---|
| 系统可用 | API 月可用性 99.9%；会话建立成功率不低于 99.5%；已确认答案丢失数 0；重复计费数 0；说完到首个回应 P95 不高于 1.5 秒 | 切文本或异步评分；熔断故障供应商；暂停新会话；核对受影响场次 | 探针、小流量和恢复演练通过，错误预算回到计划内 |
| 回答质量 | 结构化输出成功率不低于 99.5%；引用可定位率 100%；严重无依据主张率低于 0.5%；人工抽检可执行反馈通过率不低于 90% | 隔离问题或提示词版本；撤回无依据反馈；切换已验证模型 | 固定质量集和线上抽样重新达标 |
| 评分可信 | 确定性字段一致率 100%；100% 分项分数附证据与覆盖状态；重复运行跨越两个等级的比例低于 1%；核心 rubric 达到预登记人工一致性门槛 | 停止展示受影响分数；扩大人工复核；回滚评分版本 | 双评校准、题族切片和版本对照达到预登记门槛 |
| 公平合规 | 技术故障导致自动低分数 0；低置信转人工或核对率 100%；删除请求在承诺期限内完成率 100%；跨租户泄漏数 0；关键群体误差低于预登记门槛 | 暂停相关语言、题型或用途；提供文本替代、重新评估和通知；启动法律或安全流程 | 受影响结果纠正，独立复核确认风险降到允许范围 |

每类指标都要有负责人、看板和停用开关。总体满意度不能掩盖某个语言持续受损，低投诉也不能证明公平，因为受影响者可能不会申诉。样本不足时必须显示“尚不足以判断”和置信区间，不能把空白单元格涂成绿色。

### C.2 从指标到经营节奏：把线上信号变成下一版改进

**结论：上线后最重要的能力，是稳定地把故障、申诉和质量样本变成可验证改进。** 日常循环应是“收集信号 → 归因 → 版本化修改 → 离线验证 → 小流量发布 → 观察 → 扩大或回滚”。每次变化都记录原因、负责人、审批人、评测结果、发布时间和回滚位置。

| 持续经营什么 | 平时采取什么动作 | 变更前必须拿出什么 | 发布后重点观察什么 |
|---|---|---|---|
| 题库 | 新题编写、旧题复审、难度与覆盖分析、泄露处置、本地化 | 岗位相关说明、rubric、参考答案；编码题正确解全过且代表错误解失败 | 完成率、用时、跳题、分布、申诉和异常相似答案 |
| Rubric | 补充可观察信号、等级锚点、反例和证据不足条件 | 至少两名受训评审独立标注并仲裁，达到预登记一致性 | 人工改判率、等级混淆、低覆盖和切片误差 |
| 模型与提示词 | 评估新版本、固定参数、维护已校准备份 | golden set、注入、安全、成本、延迟和公平性切片通过 | 超时、格式失败、无依据主张、分数漂移和单场成本 |
| 质量样本 | 收集获准真实样本、合成边界样本、故障样本和人工标准 | 来源、许可、去标识、岗位与语言标签完整；训练和测试隔离 | 样本覆盖缺口、评审分歧和新场景退化 |
| 反馈与申诉 | 接收转写纠错、解释请求和正式申诉，追踪根因 | 处理时限、证据访问权限、升级标准和批量影响查询 | 处理时间、成立率、改判原因和重复问题 |
| 供应商与成本 | 对账调用、质量、区域、失败、账单与替换能力 | 数据条款、限流、预算、版本通知、退出和迁移方案 | 每场分项成本、重试浪费、集中度、降级率和账单差异 |
| 发布节奏 | 合并变更、影子验证、小流量、逐级放量和回滚 | 自动回归通过；高风险专项审查；完整发布清单与回滚包 | SLO、质量、分数分布、申诉、人工积压和版本采用率 |

**【建议初始目标】** 题库和 rubric 至少每季度系统复审一次，高使用量题目每月抽检；模型或提示词每次变化都运行固定质量集，不跟随供应商默认日期自动升级；线上样本每周抽取；重大申诉在 1 个工作日内确认受理、5 个工作日内给出初步结论；供应商质量与成本每周对账，至少每季度演练一次备用路径；常规发布采用每两周一个可回滚窗口，高风险评分变化单独发布并延长观察。所有频率和时限均为建议初始目标，应按业务量、适用法律和团队能力调整。

一次发布不是换一个模型名称，而是形成不可变的发布清单：题库 release、rubric、模型、提示词、转写供应商、规则、数据结构、评测报告、已知限制和回滚位置。变更先绑定真实问题或样本；自动检查状态、权限、幂等和历史兼容；再跑 golden set 与公平性切片；随后进入影子流量或小流量。异常指标越界就回滚，旧场次保留原版本，新结果以修订存在，绝不静默改写历史。

### C.3 把申诉、供应商和成本当作产品传感器

**结论：申诉不是外围客服，供应商也不是不可见黑盒；它们都是质量和经营风险的实时传感器。** 转写纠错集中在某类口音，可能说明 STT 质量退化；同一道题经常被误解，可能是题面含糊；人工频繁把三级改为二级，可能是 rubric 锚点不清；某区域晚间超时，可能是容量或路由问题。

每条反馈要归因到材料解析、题目、追问、转写、代码执行、模型、rubric、规则、报告展示、数据权利或系统故障。处理结果保留原始与修订结果、证据、责任人和影响版本。同一根因影响多场时，应主动查找范围并批量纠正，而不是等待每个人分别投诉。人工复核者看到题目、rubric、回答证据、技术状态和版本，不能只看到模型总分后进行确认式点击。

供应商看板按 provider、模型、区域、语言和 release 展示调用量、超时、P95/P99、结构成功率、fallback 去向、单位成本和版本启停时间。供应商价格具有时效性，当前报告不虚构单价；PoC 后按实际报价和压测填写 100、1,000、10,000 场三档成本模型。成本异常可能来自重试放大、上下文过长、未取消的语音合成或人工复核积压，不能只看每百万 token 的标价。

### C.4 用同一张表决定可扩量、暂缓还是回滚

**结论：扩量应采用“关键条件全部满足”，不能让漂亮的加权平均抵消一项高风险失败。**

| 当前观察到什么 | 现在采取什么决定 | 接下来必须完成什么 |
|---|---|---|
| 连续两个观察窗口达到核心 SLO；当前 release 的状态、证据、安全和 golden 门禁全过；可靠评分覆盖没有下降；关键切片达标；人工与成本有余量；2 倍目标峰值演练通过 | **可扩量**：按预先设定阶梯逐步增加流量，不一次全开 | 继续观察最差切片、错误预算、申诉、人工积压与单位成本；保留随时回滚能力 |
| 系统基本可用，但样本量不足、评分可信未达门槛，或只在部分语言/岗位稳定 | **暂缓正式扩量**：可增加内部或影子流量；按能力矩阵限制语言、岗位或题型 | 补样本、校准 rubric、修复题库或供应商路径；达到预登记门槛后重新评审 |
| 出现跨租户数据问题、样例混入正式结果、技术故障导致自动低分、隐藏测试泄露、严重评分漂移、未关闭 P0/P1，或错误预算快速燃烧 | **立即回滚或停用相关能力**：先停止结果发布和下游消费，再保全证据 | 列出受影响场次，通知、复核、重算或撤回；完成根因修复、回归和小流量验证后再恢复 |
| SLO 达标，但每场成本、重试放大或人工复核积压不可持续 | **冻结流量**：不以技术可用掩盖经营不可持续 | 调整上下文、模型路由、缓存和复核门槛；完成成本对账与容量验证 |
| 总体指标正常，但某个关键语言、设备或合理便利切片显著越界 | **缩小适用范围**：暂停受影响切片，其他已验证范围可维持 | 提供文本替代或重新评估，扩大该切片样本，完成独立公平性复核 |

仪表盘至少回答五个问题：用户是否顺利完成；证据是否足够；评分是否仍对齐共同标尺；故障影响是否受控；单位成本和人工量是否可持续。每张决策卡同时显示当前值、建议初始目标、7/28 天趋势、最大异常切片、数据完整度和当前 release。只看均值会掩盖尾部，只看总量会把流量变化误认为质量变化，只看技术成功率会忽略错误结论。

### C.5 最终经营判断

**结论：可持续经营的对象不是某个模型，而是一套能发现、止损、恢复和变好的制度。** 发现依赖贯穿整场的追踪标识、每项结论的来源记录和按语言、岗位、设备拆分的指标；止损先暂停有风险的结果，再熔断故障能力、保存已提交事实并透明降级；恢复先探针、再小流量、再逐级放量，对待处理任务幂等重放，对错误结果版本化撤回；变好则把事故、申诉、人工推翻和高分歧样本变成获准、去标识、有用途限制的测试资产。

**【事实】** 两个固定项目提供了准备、实时、会后、状态机、快照、结构化评分和代码执行边界等可复用切片；它们没有证明真实模型与语音质量、生产安全、容量、成本、招聘效度或公平性。**【建议】** 因此首版应在自主练习范围内建立证据闭环和运营闭环。招聘评估只能作为独立 Go/No-Go：岗位效度、法律审查、候选人通知、合理便利、人工复核、申诉和独立公平性评估任一缺失，都应暂缓。

<!-- EARLY-GUIDE-END -->

## 2. 证据边界与引用约定

一级证据入口为 [DeepInterview 静态证据审计](ai-interview-research/evidence/deepinterview-audit.md) 与 [GrillKit 源码证据审计](ai-interview-research/evidence/grillkit-audit.md)，二级证据为两个固定仓库源码。本章不使用浮动分支，也不把后续状态倒推到上述 HEAD。

**【事实】** DeepInterview 实际通过的仅有 Python compileall、setup Bash 语法和基础 Compose 配置解析；其 pytest、Vitest、build、真实媒体与供应商链路未运行。GrillKit 实际通过 Python compileall 和 101 个 YAML 解析；pytest、Ruff、mypy、容器、Judge0、真实模型和语音未运行。测试文件数量、CI 配置和 README 的绿色描述只能说明存在资产或作者宣称，不能写成“本次测试通过”。

**【建议】** 每个输出强制记录 `content_state`（real/mock/degraded/sample）、provider、model、prompt/rubric version、question-bank version、locale、coverage 和时间。页面、导出及分析必须携带同一 provenance，sample/mock 在数据层禁止进入正式统计。

## 3. 两项目值得借鉴与不可照搬

### DeepInterview

值得借鉴：

- **【事实】** prep/live/post 三段以 `InterviewContext` 串联；Prep 并行处理 CV、JD 和公司资料，再执行 gap matching 与选题（[prep graph](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/prep/graph.py)，[shared models](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/shared_models.py)）。
- **【事实】** LLM 输出之外保留确定性不变量：competency 绑定计划目标，分数限制在 0–5，level 由数值派生；未答题被跳过并由 coverage 表达，而非误记零分（[evaluator](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/post/evaluator.py)）。
- **【事实】** 单题失败隔离；无答案标记 `no_answers` 且不落虚假零分报告；同进程有 session 评分锁和完成态短路（[post pipeline](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/post/__init__.py)）。
- **【事实】** SessionGuard 限制时长/turn，TranscriptFlusher 周期保存，体现实时链路的崩溃恢复意识（[guard](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/live/guard.py)，[flusher](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/live/flusher.py)）。

不可照搬：

- **【事实】** `INTERNAL_API_SECRET` 为空时写端点不鉴权，读端点依赖不可猜 session id；这是本地便利，不是公网授权模型（[auth](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/api/auth.py)）。
- **【事实】** 缺 key/未知 provider 可回 MockLLM，报告页又存在 sample fallback，生产会有结果真实性风险。
- **【事实】** Supabase answer append 为 read-modify-write，评分锁仅限单进程，多实例可能丢更新或重复计费。
- **【事实】** CV URL、JD、context、transcript、scorecard 可持久化，但未见完整 retention、用户导出/删除、字段级加密与录音同意。

### GrillKit

值得借鉴：

- **【事实】** session/section/task 状态机明确，四种 session mode 决定阶段顺序，生命周期不由 LLM 决定（[session phases](ai-interview-research/repos/grillkit/app/interview/domain/session_phases.py)，[create session](ai-interview-research/repos/grillkit/app/interview/use_cases/create_session.py)）。
- **【事实】** 题目、rubric、task spec 与回答随会话快照，题库更新后仍可解释历史结果（[models](ai-interview-research/repos/grillkit/app/shared/infrastructure/models.py)）。
- **【事实】** Pydantic schema、JSON 解析与重试比自由文本评分稳健；领域事件与 WebSocket 协议分离（[structured evaluation](ai-interview-research/repos/grillkit/app/shared/structured_evaluation.py)）。
- **【事实】** 返回客户端前移除 hidden tests 和 public expected output，方向正确（[task spec](ai-interview-research/repos/grillkit/app/coding/domain/task_spec.py)）。
- **【事实】** Whisper 模型采用 staging、校验和原子 promote，适合大型资产安装（[Whisper gateway](ai-interview-research/repos/grillkit/app/shared/infrastructure/gateways/whisper_model.py)）。

不可照搬：

- **【事实】** 判题框架存在不代表题库成熟；当前 44 道编码题均无真实 public/hidden tests。
- **【事实】** 项目无认证且 Compose 发布 8000；审计未发现完整 CSRF、WebSocket Origin、TrustedHost 和 CSP 防护。
- **【事实】** 默认 root 路径在 migration 前 `exec gosu`，后续 migration 不可达（[entrypoint](ai-interview-research/repos/grillkit/docker-entrypoint.sh)）。
- **【事实】** Judge0 server/worker 使用 privileged，示例密码不适合共享网络；Monaco 从 CDN 加载且无 SRI。
- **【事实】** API key、答案、代码和输出可明文落盘；音频路由一次性读取上传文件且未见路由级体积限制。

## 4. 横向比较表

| 维度 | DeepInterview | GrillKit | 产品结论【建议】 |
|---|---|---|---|
| 定位 | CV/JD 定制的语音模拟 | 本地理论+编码训练 | 首版只做自主练习 |
| 编排 | prep/live/post、LangGraph | 确定性状态机 | 状态机主导，LLM 只做受约束语义任务 |
| 语音 | LiveKit、多 STT/TTS | Whisper/Piper、本地音频 | 语音可选，文本必须可降级 |
| 编码 | 角色问答为主 | Judge0 Run/Submit 框架 | 确定性测试优先，AI 反馈辅助 |
| 评分 | competency、coverage、报告 | 1–5 分、追问、总评 | 分数附证据、覆盖率、版本和不确定性 |
| 数据 | Memory/Supabase | SQLite/SQLAlchemy/Alembic | 不可变快照、事务、幂等、删除链 |
| 已验证范围 | 三项轻量静态/配置验证 | compileall 与 YAML 解析 | 必须自建完整质量门禁 |
| 关键缺口 | provenance、真实语音、治理、跨实例一致性 | 无真实测试题、迁移缺陷、共享部署风险 | Beta 前关闭安全、内容、校准问题 |

## 4A. 推荐技术蓝图

本章给出拟建系统的目标技术形态，避免与后文用途、合规、团队和交付路线重复。**【事实】** DeepInterview 提供 prep/live/post、实时媒体与 `InterviewContext` blackboard 的可复用切片；GrillKit 提供确定性 session/section/task、题目快照、领域事件、结构化评分与 Judge0 边界的可复用切片。**【未验证】** 两个固定 HEAD 均未完成真实 LiveKit、STT/LLM/TTS、完整 RAG、Judge0、生产数据库和端到端容量验证。**【建议】** 组合两者的边界，而不是复制任一默认部署：状态机与数据库控制事实，LLM 只承担受约束的语义任务，实时媒体、长任务、代码执行和数据存储分成独立故障域。

### 4A.1 总体组件架构

```mermaid
flowchart LR
    U["候选人 Web / Mobile"] --> EDGE["Gateway / Auth / Rate Limit"]
    ADMIN["题库与运营后台"] --> EDGE
    subgraph CONTROL["控制面"]
        API["Session API"]
        SM["State Machine"]
        PREP["Prep Orchestrator"]
        POST["Post Orchestrator"]
        BANK["Question Bank"]
        REG["Provider Registry"]
    end
    subgraph LIVE["实时面"]
        RTC["WebRTC / LiveKit"]
        VOICE["Voice Worker"]
        VAD["VAD + Turn Detector"]
        STT["Streaming STT"]
        LLM["Low-latency LLM"]
        TTS["Streaming TTS"]
    end
    subgraph ASYNC["异步与隔离执行"]
        Q["Durable Queue"]
        RAG["RAG Workers"]
        SCORE["Scoring Workers"]
        JG["Judge0 Gateway"]
        J0["Isolated Judge0"]
    end
    PG[("Postgres")]
    OBJ[("Object Storage")]
    VEC[("Knowledge Store")]
    REDIS[("Redis")]
    OBS[("Metrics / Logs / Traces")]
    EDGE --> API --> SM
    SM --> PREP
    SM --> POST
    PREP --> BANK
    PREP --> Q
    POST --> Q
    Q --> RAG --> VEC
    Q --> SCORE --> PG
    API --> PG
    API --> OBJ
    U <--> RTC <--> VOICE
    VOICE --> VAD --> STT --> LLM --> TTS --> VOICE
    VOICE --> PG
    VOICE --> REDIS
    VOICE --> REG
    API --> JG --> J0
    JG --> PG
    CONTROL --> OBS
    LIVE --> OBS
    ASYNC --> OBS
```

**【建议】** Session API 是鉴权后的命令与查询入口；State Machine 是会话状态唯一写入者；Prep/Post 承担可重试长任务；Voice Worker 只持有短生命周期上下文并写 committed turn；Judge0 Gateway 隔离内部测试与客户端安全视图；Provider Registry 根据能力、语言、地区、数据政策、健康度、成本和超时路由。Postgres 保存事务事实，对象存储保存大对象，Redis 只承载短期 lease/presence/cache，知识库按 tenant 与 session 强制分区。异步任务通过事务 outbox 发布，避免数据库已提交而事件丢失。

### 4A.2 Prep / Live / Post

**Prep。【事实】** DeepInterview 的 prep 图并行处理 CV、JD 和公司资料，汇合后做 gap matching 与 question planning（[prep graph](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/prep/graph.py)）；CV 解析支持文本、data URL 和远程 URL，因此也存在 SSRF、重定向、体积与恶意文档风险。**【建议】** Prep 分为接收与隔离解析、结构化抽取、差距分析、题目规划、快照发布。解析层先做 MIME、页数、解压体积、跳转、DNS/IP 和恶意载荷检查；最终 `PlanSnapshot` 固定题库 release、question revision、rubric、locale、citation、provider 和模型版本。输入无效进入拒绝态，外部服务局部失败进入 degraded 态，不能静默回 mock 后继续标记为真实结果。

**Live。【事实】** DeepInterview worker 从房间元数据解析 session id，经 API 取得已准备 context，构造 VAD/STT/LLM/TTS 的 `AgentSession`，捕获 committed transcript，并用 guard 限制会话（[live worker](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/worker.py)）。GrillKit 的 section、timer 和追问深度由服务端领域规则约束。**【建议】** Live 只读不可变 plan snapshot；partial transcript 仅用于即时界面，只有 `turn.committed` 才是评分事实。语音、文本和代码统一抽象为 Attempt，但媒体、代码与执行结果分开存储。题目计时、追问、section 切换和结束必须由服务端验证，前端不可自行宣告完成。

**Post。【事实】** DeepInterview 对已回答题执行有界并发评分，未答题不记零分而由 coverage 表达；competency 绑定计划目标，分数限制和 mastery band 由代码确定（[post evaluator](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/post/evaluator.py)）。**【建议】** Post 先冻结 transcript/attempt 输入哈希，再并行执行 rubric 评分、语言分析、代码信号汇总、引用核验和报告生成。报告显示 coverage、degraded reason、题库/rubric/prompt/provider/model 版本和证据片段。无有效答案返回 `NO_EVIDENCE`，不得产出貌似精确的低分画像；同一输入哈希和 rubric 版本只允许一个评分结果生效。

### 4A.3 会话状态机

```mermaid
stateDiagram-v2
    [*] --> DRAFT
    DRAFT --> PREP_QUEUED: submit_prep
    PREP_QUEUED --> PREPARING: worker_claimed
    PREPARING --> PREP_REJECTED: invalid_input
    PREPARING --> PREP_DEGRADED: partial_failure
    PREPARING --> READY: plan_published
    PREP_DEGRADED --> READY: accept
    PREP_DEGRADED --> PREP_QUEUED: retry
    PREP_REJECTED --> DRAFT: revise
    READY --> CONNECTING: join
    CONNECTING --> LIVE: media_ready
    CONNECTING --> READY: connect_failed
    LIVE --> RECONNECTING: transport_lost
    RECONNECTING --> LIVE: resumed
    RECONNECTING --> DRAINING: reconnect_timeout
    LIVE --> DRAINING: finish_or_guard
    DRAINING --> POST_QUEUED: checkpointed
    POST_QUEUED --> SCORING: worker_claimed
    SCORING --> REPORT_DEGRADED: partial_failure
    SCORING --> COMPLETED: report_committed
    REPORT_DEGRADED --> COMPLETED: accepted_or_repaired
    COMPLETED --> [*]
```

**【建议】** 每次状态迁移携带 `expected_version`，数据库执行 compare-and-swap；版本不匹配返回冲突，不重复调用外部服务。`DRAINING` 停止发新题，但允许已承诺音频、transcript、usage 和最终 checkpoint 落盘。Section 子状态使用 `PENDING → ACTIVE → EVALUATING → COMPLETED|SKIPPED`，Attempt 子状态使用 `CREATED → ANSWERING → SUBMITTED → EVALUATING → SCORED|FAILED|TIMED_OUT`。LLM 输出永远不能直接修改这些状态。

### 4A.4 实时语音、barge-in、延迟预算与降级

**【事实】** DeepInterview 使用预热 Silero VAD；可支持语言使用 multilingual turn detector，其他语言回退静音 endpointing；barge-in 要求已形成转写词后才确认中断，以减少背景噪声切断面试官（[turn handling](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/worker.py)）。BVC 降噪是显式 opt-in。审计没有得到真实口音、噪声、设备和供应商延迟数据。

**【建议】** 链路为浏览器音频帧 → WebRTC → 降噪/增益 → VAD → streaming STT → semantic turn detector → LLM preemptive generation → streaming TTS。候选人开口时先降低播放音量；达到 VAD/STT 门槛后取消当前 generation、清空未播放 TTS buffer，记录 `assistant.interrupted` 及已播放区间。所有 token、音频块和取消操作携带 generation id，防止上一轮迟到结果污染新轮。

下表全部是**建议初始目标**，不是两个仓库的实测结果：

| 环节 | 建议初始目标 |
|---|---:|
| 浏览器到 VAD 可用帧 | P95 不高于 80 ms |
| VAD 起音检测 | P95 不高于 120 ms |
| 首个 STT partial | P95 不高于 300 ms |
| 语义端点判定 | P95 不高于 450 ms |
| LLM 首 token | 云端 P95 不高于 600 ms；本地热模型 P95 不高于 1200 ms |
| TTS 首音频块 | P95 不高于 350 ms |
| 用户结束到助手首音 | P95 不高于 1.5 s，P99 不高于 2.5 s |
| barge-in 停声 | P95 不高于 250 ms |
| transcript checkpoint | 每 2 个 committed turn 或 5 s，取先到者 |

**【建议】** 指标按语言、设备、网络、provider 与冷热状态分桶。语义 turn detector 失败时降为静音 endpointing；主 STT 失败切备用或文本输入；TTS 失败继续显示文本；LLM 超时执行受限重试或备用模型；仍失败则透明暂停或结束。任何降级都写入 provenance，Judge0、RAG 或评分供应商失败不得被伪装成正常完成。

### 4A.5 RAG 与知识边界

**【事实】** DeepInterview 在未配置远程知识服务时使用 deterministic MockKnowledge，配置后调用 HTTP sidecar；sidecar 默认 NaiveRAG，可选完整 LightRAG。Prep 以 session id ingest CV/JD/company，Coach 使用同一 session 查询（[knowledge adapter](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/core/adapters/knowledge.py)、[RAG backend](ai-interview-research/repos/DeepInterview/services/lightrag/src/lightrag_service/backend.py)）。完整后端与真实质量未验证。

**【建议】** 划分 `candidate_private/{tenant}/{session}`、`question_bank/{release}`、`company_public/{snapshot}`，查询必须携带 tenant filter，禁止跨租户联合召回。文档记录 source URI、内容哈希、解析器版本、chunk span、embedding 版本、许可与 retention；召回结果返回 citation、chunk id、分数和索引版本。题目生成优先遵循结构化 CV/JD 与题库约束，检索文本不能覆盖系统规则。建议初始目标：RAG 查询 P95 不高于 250 ms、top-k 为 6、单次注入总预算不高于 8,000 tokens；RAG 失败时允许使用已发布计划，但明确标记未增强。

### 4A.6 题库、编码与 Judge0

**【事实】** GrillKit 对题目、rubric、starter code 和 task spec 做会话快照，客户端序列化会移除 hidden tests 与公开测试 expected output（[task spec](ai-interview-research/repos/grillkit/app/coding/domain/task_spec.py)）。Judge0 gateway、Run/Submit 和 compile/test 流程存在；但固定题库 44/44 道编码题都是 AI 模式，tests 模式为 0、public tests 为 0、hidden tests 为 0，因此当前题库实际是 compile-only 加 AI 评价，不是已具备真实公开/隐藏测试的判题产品。

**【建议】** 题库采用 `Question → Revision → Locale → Rubric → TestSuite` 的不可变 release。创建 session 时快照用户可见内容和版本；hidden tests 只保存受限引用，不进入通用 session JSON、客户端、日志、备份导出或 LLM prompt。发布流水线校验 schema、唯一 ID、本地化完整性、reference solution、错误解法、资源上限、输出规范化和客户端泄漏。

**【建议】** Judge0 经独立 Gateway 按题库版本补齐测试，执行节点放在专用 VM/节点池，默认无外网、无生产秘密、与 API/数据库隔离，不复用 GrillKit 的 privileged 共享部署。以下均为建议初始目标：执行队列等待 P95 不高于 1 s；单测试 CPU 不高于 3 s、墙钟不高于 5 s、内存不高于 128 MiB、输出不高于 64 KiB；每会话并发执行数为 1；每题 Run 上限为 20 次。具体限制须按语言和题型压测后修订。

### 4A.7 评分证据链

**【建议】** 评分融合理论 rubric、答案证据、追问表现、确定性测试、代码工程质量和语言报告；语言流利度不经岗位效度与公平性校准，不进入技术总分。每条 `ScoreEvidence` 保存 question revision、answer/turn span、test result hash、rubric、provider/model/prompt 版本、原始结构化输出、代码规则调整和最终分。确定性测试优先于模型印象，隐藏测试失败导致的分数上限由服务端代码执行，不能只写在 prompt。

**【事实】** DeepInterview 已把 competency identity、分数范围、mastery band 和 coverage 作为代码不变量；GrillKit 通过 Pydantic schema 与 JSON 重试约束模型输出，但两者都没有证明招聘效度或跨语言公平性。以下均为建议初始目标：单 worker 逐题评分并发为 4；单题超时不高于 20 s；报告生成 P95 不高于 60 s；结构化解析成功率不低于 99.5%；确定性字段在重复输入下的一致率为 100%。人工一致性、公平性 slice 与置信区间须由真实校准集建立门槛，不能预设为已达标。

### 4A.8 数据模型

**【建议】** 核心实体为：`InterviewSession(state, version, mode, locale, plan_snapshot)`；`Section(kind, order, state, time_budget)`；`QuestionRevision(locale, rubric, content_hash, bank_release)`；`Attempt(round, status, idempotency_key, input_hash)`；`TranscriptTurn(sequence, speaker, committed, timestamps, provider)`；`CodeSubmission/TestRun`；`ScoreEvidence/ScoreCard`；`KnowledgeDocument/Chunk`；`ProviderCall`；`DomainEvent/Outbox`。PII 与面试事实分离，录音和大文档进入对象存储，主库保存短期引用、哈希、owner、purpose、region 和 retention 标签。

**【事实】** DeepInterview 的 Supabase `append_answer` 是 context read-modify-write，多 worker 下存在 lost update 风险（[repository](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/core/persistence/repository.py)）；其同进程评分锁也不能跨实例互斥。GrillKit 的题面与 task spec 快照可保持历史可解释（[models](ai-interview-research/repos/grillkit/app/shared/infrastructure/models.py)）。**【建议】** Answer 与 Transcript 使用 append-only 行和单调 sequence，blackboard JSON 仅作读模型；状态表使用版本列，所有删除覆盖主库、对象存储、RAG、缓存和分析副本。

### 4A.9 API、事件与 Provider Protocol

**【事实】** DeepInterview 提供 prep、session、live result、score 和 KB API；GrillKit 的领域服务产生 AnswerSaved、Evaluating、Transcript、AnswerFeedback、InterviewCompleted，再映射为 WebSocket 消息（[wire protocol](ai-interview-research/repos/grillkit/app/theory/api/ws_protocol.py)）。这种领域事件与传输协议分离的做法值得保留。

**【建议】** 命令面包含创建 session、发起 prep、申请短期房间 token、提交 attempt、运行代码、结束 session；每个写请求携带 `Idempotency-Key` 和 `expected_version`。查询面提供 session、plan、实时投影、operation 和 report。事件 envelope 统一包括 event id/type、schema version、aggregate id/version、correlation/causation id、occurred_at、producer 和 payload；公开投影不得包含 hidden tests、密钥或无限制 prompt。

**【建议】** Provider Protocol 按能力拆为 `LLM.complete/stream`、`STT.stream`、`TTS.stream`、`Embedding.embed`、`Search.search`、`Knowledge.ingest/query`、`CodeExecutor.run`。请求统一携带 deadline、cancel token、tenant/session/turn id、locale 与 data policy；返回 usage、latency、provider request id、model version、finish reason、retryability 和 provenance。业务节点只依赖协议，不内嵌厂商条件分支。

### 4A.10 并发、幂等与一致性

**【建议】** 会话状态使用 optimistic version；Attempt 使用 `(session_id, question_revision_id, round)` 唯一约束与幂等键；外部昂贵任务使用 durable queue lease。采用 at-least-once 事件投递加幂等消费者，以数据库唯一键实现 exactly-once effect，而不宣称无法证明的 exactly-once delivery。事务 outbox 保证事实写入与事件发布可恢复，consumer inbox 防止重放。

以下均为建议初始目标：同一 session 同时只有 1 个 live lease；版本冲突返回 409 且外部副作用为 0；队列最多重试 3 次并指数退避；熔断观察窗口为 30 s；最终 checkpoint 的 RPO 不高于 5 s；控制面 RTO 不高于 15 min。单题失败不得清除其他结果，评分全失败进入 degraded，而不是写成完整零分；生产不得自动回 MockLLM 后输出 real 标记。

### 4A.11 前端边界与多语言

**【建议】** 前端负责设备权限、波形、partial transcript、断线重连、编辑器草稿、反馈解释和无障碍；后端负责 token、owner/tenant 授权、timer、状态迁移、attempt 接受、题库可见性和评分。浏览器中的倒计时、“已提交”和 partial 文本均为 optimistic projection，最终由服务端 committed event 校正。Monaco 等执行界面资源自托管并固定哈希，不沿用无 SRI 的动态 CDN。

**【事实】** DeepInterview 按 primary language 路由实时 STT/TTS，但语义 turn detector 覆盖有限；GrillKit 的题库 locale 缺失时回退英语。**【建议】** 分离 `ui_locale`、`question_locale`、`candidate_speech_locale`、`voice_locale`、`evaluation_locale`，每次 fallback 写入 provenance。以下均为建议初始目标：正式 locale 的核心 UI 文案覆盖率为 100%；题目与 rubric 成对发布覆盖率为 100%；fallback 率低于 1%。WER/CER 不设置无数据承诺，先以许可媒体集按语言、口音、设备和噪声建立基线。

### 4A.12 基础设施与可观测性

**【建议】** 部署划分 edge、control、realtime、async、sandbox、data 安全域。Web/API/worker 非 root、只读文件系统、固定镜像 digest；Judge0 位于独立节点并默认断网；Postgres 保存事务事实，Redis 不作为事实源；对象存储使用短期签名 URL；向量查询强制 tenant namespace。生产启动 fail closed：认证、迁移、secret、数据库、对象存储或 provider policy 缺失时拒绝相应能力，禁止沿用 trust-the-network。

可观测性以 session trace 串联 prep operation、媒体房间、turn、provider call、Judge0 submission、score job 与 outbox。指标包括状态冲突、队列时延、音频 jitter/丢包、VAD false-start、STT partial/final latency、turn endpoint、LLM TTFT、TTS TTFB、barge-in、provider timeout/retry/circuit、usage/cost、Judge0 queue/run、coverage、degraded rate、数据库冲突和 outbox lag。日志默认不保存 CV、JD、transcript、代码、prompt 与 API key；受控调试也要脱敏、抽样和短保留。

以下均为建议初始目标：API 可用性为 99.9%；实时会话建立成功率不低于 99.5%；未解释 live 中断率低于 1%；状态事件到查询投影 P95 不高于 2 s；outbox lag P95 不高于 5 s；trace 关联完整率不低于 99%；敏感字段自动扫描泄漏数为 0。目标在 PoC 压测和真实错误预算形成后修订，不能倒写成固定仓库已有能力。

## 5. 候选人练习与招聘评估边界

**【建议：练习范围】** 用户自主选择岗位、上传或粘贴材料、完成模拟问答/编码并获得形成性反馈。可以展示能力维度、回答证据、覆盖率、改进建议和示例答案，但应称“练习反馈”，不宣称录用概率或代表雇主标准。简历不是必填，练习数据默认不流向招聘客户，也不得未经独立同意进入训练集。

**【建议：招聘评估范围】** 一旦结果被雇主用于筛选、排序、淘汰或晋级，即进入高风险评估。必须另行定义适法基础、候选人通知、岗位相关性、合理便利、人工复核、申诉纠错、地域与保留策略、子处理商和客户合同。自动分不得成为唯一不利决定依据；低覆盖、技术故障、低 STT 置信或模型异常应自动转人工，而非判低分。

禁止用练习次数、付费状态、摄像头质量、背景噪声、口音、停顿、面部或情绪推断等缺乏岗位效度的信号评分。

### 明确排除真实面试作弊

**【建议/硬边界】** 不构建、不宣传、不支持：隐蔽监听真实第三方面试并实时生成答案；不可见提词器或绕过屏幕共享；冒名代答、声音/人脸伪造；规避监考或身份核验；窃取、重建或泄露雇主隐藏题库。实时音频只能用于产品内明确标识的模拟房间。营销、客服、模板和滥用处置必须保持一致。

## 6. 产品与合规准备

**【建议】** 建立“用途—数据—决策”登记：谁发起、数据来源、进入哪些模型、保存多久、影响谁、是否产生不利决定。上线前由适用司法辖区律师复核劳动、隐私、自动化决策、录音/生物识别和消费者保护要求；本章不构成法律意见。

最低准备包括：候选人和企业客户两套条款；隐私通知与子处理商清单；DPA；录音/转写单独提示；数据下载、删除、纠错与撤回入口；无障碍文本替代；人工复核和申诉 SLA；安全事件流程；模型/题库变更记录；禁止作弊与禁止高风险推断政策。

生产配置必须 fail closed：认证、持久化、provider、对象存储或区域策略缺失时拒绝启动相应能力，不得回 mock 后继续产生正式分数。样例只存在演示 tenant。

## 7. 隐私、安全威胁模型与数据治理

| 资产/入口 | 威胁 | 控制【建议】 |
|---|---|---|
| CV/JD/逐字稿/录音/分数 | 越权、URL 泄露、日志与存储误配 | user/tenant 授权、短签名 URL、加密、默认不留原音频 |
| API 与模型额度 | 空 secret、重放、批量消耗 | OIDC/JWT、RBAC、幂等键、限流、预算熔断 |
| URL/文件导入 | SSRF、DNS rebinding、恶意 PDF、压缩炸弹 | 禁私网/metadata、逐跳重验、egress proxy、大小/MIME/页数限制、隔离解析 |
| Prompt/RAG | 文档注入、秘密外带、评分操纵 | 输入视为不可信、工具 allowlist、秘密不入 prompt、schema 与引用隔离 |
| WebSocket/媒体 | Origin 欺骗、token 泄露、会话接管 | WSS、Origin/Host allowlist、短期单房间 token、重放保护 |
| 代码执行 | 容器逃逸、挖矿、内网扫描 | 专用 VM/节点、无外网、只读根、seccomp/cgroup、销毁 workspace |
| 隐藏测试 | 客户端、日志、备份、内鬼泄露 | 独立加密、最小权限、client contract test、审计和轮换 |
| 供应链 | latest 镜像、CDN、非 frozen 安装 | digest/hash pin、SBOM、签名、自托管静态资源、扫描 |
| 一致性 | 重连重复提交、lost update | version/ETag、事务 append、outbox、分布式锁 |

**【建议：数据治理】** 数据至少分为账户信息、职业材料、面试内容和派生评分四级；每个字段登记目的、来源、tenant、区域、保留期、接收方、训练资格和删除路径。原始音频默认只用于实时转写；需回放时单独选择。删除覆盖主库、对象存储、RAG 索引、缓存、分析仓及备份到期清除，并提供状态、重试和完成凭证。训练用途必须独立 opt-in、去标识、授权审查且可撤回。生产数据禁止复制到个人调试环境。

## 8. 公平性与评分校准

**【事实】** DeepInterview 有分数范围、competency identity 和 coverage 的代码约束，GrillKit 有结构化 schema；两份审计均未证明招聘效度、公平性、跨语言一致性或真实媒体质量。结构化输出不等于可信评分。

**【建议】** 评分对象应是“在给定岗位相关题和 rubric 下展示的可观察证据”，而非候选人整体。报告展示题目/rubric/模型版本、证据片段、规则信号、覆盖率和人工修改。禁止以受保护属性及其代理变量评分；STT 低置信时允许核对转写，以文本修正为准。

校准集覆盖岗位、级别、题型、语言、口音、回答长度、设备/噪声和合理便利；每条由至少两名受训领域评审独立标注并仲裁。按候选人和题族隔离数据集，避免泄漏。指标至少包括人工一致性、相邻等级准确率、重复运行方差、缺失处理、覆盖率、各群体误差与置信区间。样本不足只能报告证据不足，不能宣称“无偏”。模型或 prompt 升级必须通过固定 golden set 回归。

## 9. 测试矩阵与质量门禁

| 层级 | 必测内容 | 门禁【建议】 |
|---|---|---|
| 静态/供应链 | lint、type、secret、SBOM、许可证、锁文件 | 高危秘密、关键漏洞、非固定生产依赖阻断 |
| 单元/属性 | 状态机、timer、score clamp、coverage、权限 | 关键不变量全过并 fuzz/property test |
| 题库 | schema、ID、locale、rubric、golden、错误解法 | tests-mode 题 golden 全过、代表错误必须失败 |
| API/并发 | schema、幂等、重放、版本冲突 | 不重复计费/写入；客户端无 hidden expectation |
| 迁移 | 空库、升级、备份恢复 | 自动到 head，数据与约束一致 |
| E2E | setup→回答→报告→导出/删除、断线 | 无 sample 混入真实结果，断线不丢已确认答案 |
| 媒体 | 噪声、口音、静音、barge-in、设备切换 | 失败可转文本，转写可纠错 |
| 模型 | golden、注入、长输入、语言/公平性 slice | 不达门槛则不评分或转人工 |
| 安全 | IDOR、SSRF、CSRF/Origin、上传、沙箱、限流 | P0/P1 未关闭不得 Beta/生产 |
| 性能/灾备 | p95/p99、峰值、超时、故障注入、恢复 | 达 SLO；删除、密钥轮换、RPO/RTO 演练通过 |

当前两个仓库的轻量检查只能作为输入，不构成上述门禁已经满足。

## 10. 团队、硬件、API 与数据集准备

**【建议：团队】** 覆盖产品、前后端/平台、实时音频、ML 评估、数据、安全、隐私/法务、招聘测量、题库内容、QA/SRE、无障碍和用户研究。PoC 可兼任，但安全、法务和评分效度不能由实现者自审自批。

**【事实】** DeepInterview 本地 profile 包含 `qwen3:8b`、Whisper、Kokoro；GrillKit 的 Whisper 规格约 0.5/1.5/3 GB，Piper 单 locale 约 60 MB 的数字来自项目材料，审计没有运行性能验证。

**【建议：硬件】** CI 使用无 GPU mock 和录制 fixture；媒体环境准备 Linux CPU 节点、真实设备矩阵与网络整形。本地 8B 模型可先用约 24GB VRAM 的单卡作为基准候选，但并发必须压测后承诺。代码沙箱与应用、数据库、秘密隔离到专用 VM/节点。

**【建议：API】** LLM、STT、TTS、媒体、存储、搜索和认证均准备 sandbox/production 双账户，登记区域、保留、训练使用、限流、SLA、DPA 和退出能力。STT 失败转文本、TTS 失败显示题目、搜索失败不阻断、评分失败保存答案后异步重试。密钥只进 secret manager。

**【建议：数据集】** 准备版本化题库/rubric、人工校准集、媒体质量集和安全对抗集。编码题必须有 golden solution、public/hidden cases、错误解法及资源预算。记录来源、许可证、PII、岗位范围和禁止用途。

## 11. 成本、容量与 Build vs Buy

**【建议】** 单场成本按 `prep LLM + live LLM + STT 分钟 + TTS + post 多题评分 + 搜索/RAG + 媒体房间 + 存储/出网 + 沙箱 + 可观测性 + 人工复核` 建模。峰值并发房间约为“峰值每小时到达量 × 平均会话分钟 ÷ 60”；评分容量由题数、调用时延、provider 并发和报告时限决定。设置 session 时长、turn、题数、上传、Run 次数、tenant/provider 月预算和重试幂等上限。供应商价格具有时效性，PoC 后以实际报价和压测填写 100/1,000/10,000 场三档模型，不虚构单价。

| 能力 | 决策【建议】 | 理由 |
|---|---|---|
| 状态机、题库、rubric、证据链、申诉 | Build | 核心差异与审计责任 |
| LLM/STT/TTS | 先 Buy，保留 adapter | 降低早期运维，保留替换权 |
| 实时媒体 | 托管优先 | WebRTC 和设备兼容复杂 |
| 认证、存储、数据库 | 成熟托管优先 | 采用企业级标准控制 |
| 编码沙箱 | 隔离托管或专用集群 | 不复用 privileged 默认方案 |
| 公平性/效度 | 内建标准，可外聘独立审计 | 责任不能外包 |

## 12. PoC / MVP / Beta / 生产路线图及退出条件

**PoC：离线文本与证据链。** 固定题库、mock、结构化 rubric、快照、provenance、导出/删除样机，只用合成或许可数据。退出条件：状态机与不变量通过；sample/mock 明确；题库 schema/ID 通过；能追溯反馈到题目、rubric 和回答证据；威胁模型与数据目录签字。

**MVP：受控练习。** 加账户授权、可选 CV/JD、文本主路径、可选语音、provider sandbox、纠错、删除、预算和观测；编码只上线有可靠测试的题。退出条件：E2E、迁移、SSRF/上传、权限、Origin、删除传播通过；P0/P1 清零；媒体可降级；100 场内部/合成容量测试满足 SLO，无答案丢失和重复计费。

**Beta：邀请制练习。** 加有限多语言、人工客服/申诉、nightly provider 回归、红队、无障碍和成本仪表盘，仍禁止用于淘汰。退出条件：预注册质量与稳定性门槛达到；关键语言/设备/口音 slice 无无法解释落差；独立渗透测试、恢复、轮换、删除抽样和 2 倍峰值压力通过。

**生产：自主练习 GA。** 建立 on-call、错误预算、回滚、供应商退出、持续校准。退出条件：连续两个发布周期无未解决 P0/P1；模型/题库版本与季度访问审查、年度渗透/灾备演练落地。

**招聘评估受限试点：独立 Go/No-Go。** 必须完成岗位效度、法律审查、通知、合理便利、人工复核、申诉、合同限制和独立公平性评估；任一缺失即 No-Go。只输出供人工参考的证据包，不发自动录用/淘汰指令。

## 13. 风险登记表

| ID | 风险 | 概率/影响 | 缓解与退出条件【建议】 |
|---|---|---|---|
| R1 | 练习分被用于自动淘汰 | 中/极高 | 用途合同、API scope、审计；不存在自动不利决定路径 |
| R2 | mock/sample 冒充真实 | 中/高 | 强 provenance；契约测试证明不进入正式指标 |
| R3 | 未校准分数不公平 | 高/极高 | 双评审校准、slice 指标、转人工；达预注册门槛 |
| R4 | 敏感材料泄露 | 中/极高 | 最小化、加密、授权、短保留；删除抽样通过 |
| R5 | 空认证/IDOR | 中/极高 | OIDC/RBAC、tenant scope；越权测试通过 |
| R6 | SSRF/恶意文档 | 中/高 | egress、DNS 重验、隔离解析；红队不能访问内网 |
| R7 | 沙箱逃逸 | 低中/极高 | 专用节点、无网、cgroup；独立评估通过 |
| R8 | 重复评分/丢答案 | 中/高 | 事务、版本、幂等、outbox；故障注入通过 |
| R9 | 迁移破坏可用性 | 中/高 | 显式 migration job；空库、升级、恢复通过 |
| R10 | 题库测试名存实亡 | 高/高 | golden/错误解法/hidden 门禁；上线题全过 |
| R11 | 供应商限流或涨价 | 中/高 | adapter、降级、预算熔断、退出演练 |
| R12 | 真实面试作弊用途 | 中/高 | 产品禁能、政策与处置；无隐蔽监听/提词功能 |
| R13 | 供应链污染 | 中/高 | pin、SBOM、签名、自托管；发布扫描通过 |
| R14 | STT 误差变成低分 | 中/极高 | 转写确认、文本替代；低置信不评分/转人工 |

## 14. 上线 Checklist

- [ ] 用途明确为自主练习，招聘评估未混入默认产品。
- [ ] 真实面试作弊排除项进入需求、营销、客服和安全测试。
- [ ] 代码、模型、prompt、rubric、题库和 schema 版本可追溯。
- [ ] 生产禁用 mock/sample 正式评分，degraded 状态清晰。
- [ ] OIDC/服务身份、tenant 授权、媒体短 token、限流与预算熔断启用。
- [ ] CV/JD/音频/逐字稿有目的、区域、保留、删除、导出和训练资格。
- [ ] SSRF、恶意文件、Origin/Host、CSRF、TLS、CSP 与重放测试通过。
- [ ] 代码执行专用隔离、无秘密、默认无外网、无 privileged 共享部署。
- [ ] 上线编码题均有 golden、public/hidden tests 和错误解法验证。
- [ ] 空库/升级/备份恢复通过，迁移路径可达。
- [ ] append/submit/score/delete 有幂等和跨实例一致性测试。
- [ ] 质量、稳定性、公平性和 prompt injection 回归达门槛。
- [ ] 低覆盖、低 STT 置信和技术故障不会自动变低分。
- [ ] 文本替代、纠错、人工复核和申诉 SLA 可用。
- [ ] SBOM、许可证/NOTICE、依赖/镜像扫描和静态资源自托管完成。
- [ ] SLO、容量、成本、限额、告警、轮换、恢复和事件演练通过。

## 15. 两个项目关键缺口

**DeepInterview：**（1）真实媒体、provider、存储与 RAG 端到端未验证；（2）sample/mock/degraded 缺少贯穿全链路的强 provenance；（3）空 secret、capability-only read、SSRF 和跨实例一致性不足；（4）敏感数据 retention、删除/导出、录音同意和区域治理不完整；（5）缺招聘效度、人工校准与跨语言公平性证据。

**GrillKit：**（1）44 道编码题均无 public/hidden tests，内容未兑现执行框架；（2）默认 root entrypoint 的 migration 不可达；（3）无认证及 CSRF/Origin/Host/CSP、base URL 和明文 key 风险；（4）privileged Judge0、示例密码和 CDN Monaco 不适合共享生产；（5）完整 CI、真实模型/语音、E2E、容量、公平性和成本未验证。

## 16. 本地研究入口和阅读顺序

1. 先读 [DeepInterview 审计](ai-interview-research/evidence/deepinterview-audit.md) 的执行摘要、流程、安全、测试和限制。
2. 再读 [GrillKit 审计](ai-interview-research/evidence/grillkit-audit.md) 的执行摘要、题库、迁移、安全、测试和限制。
3. DeepInterview 主链路：[prep graph](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/prep/graph.py) → [worker](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/worker.py) → [evaluator](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/post/evaluator.py) → [report](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/post/report.py)。
4. DeepInterview 边界：[auth](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/api/auth.py) → [repository](ai-interview-research/repos/DeepInterview/apps/agent/src/deepinterview_agent/core/persistence/repository.py) → [Supabase migration](ai-interview-research/repos/DeepInterview/supabase/migrations/0001_init.sql) → [报告页](ai-interview-research/repos/DeepInterview/apps/web/app/report/[id]/page.tsx)。
5. GrillKit 主链路：[session phases](ai-interview-research/repos/grillkit/app/interview/domain/session_phases.py) → [create session](ai-interview-research/repos/grillkit/app/interview/use_cases/create_session.py) → [structured evaluation](ai-interview-research/repos/grillkit/app/shared/structured_evaluation.py) → [submit solution](ai-interview-research/repos/grillkit/app/coding/use_cases/submit_solution.py)。
6. GrillKit 判题/部署：[task spec](ai-interview-research/repos/grillkit/app/coding/domain/task_spec.py) → [run tests](ai-interview-research/repos/grillkit/app/coding/use_cases/run_tests.py) → [Judge0](ai-interview-research/repos/grillkit/app/shared/infrastructure/gateways/judge0.py) → [Compose](ai-interview-research/repos/grillkit/docker-compose.yml) → [entrypoint](ai-interview-research/repos/grillkit/docker-entrypoint.sh)。
7. 最后读 [DeepInterview README](ai-interview-research/repos/DeepInterview/README.md) 和 [GrillKit README](ai-interview-research/repos/grillkit/README.md)，只用于作者意图和配置说明，并与审计实际执行结果对照。

结论是：两个项目都提供了值得复用的工程切片，但没有一个固定 HEAD 已证明可直接用于真实招聘决策。应复用状态机、证据链、结构化契约、失败隔离和 provider adapter，同时重建认证、数据治理、评分校准、沙箱、安全测试与阶段退出机制。第一性边界是帮助候选人练习，而不是在真实面试中作弊，也不是用未经验证的模型分数替代人的招聘责任。
