# Phase 2 实时 ASR 评测协议

状态：协议草案，尚未绑定样本，尚无结果。任何执行都必须先在 [样本状态](SAMPLE_STATUS.md) 登记真实音频和 reference。

## 1. 要回答的问题

Phase 2 不复测“一个音频文件最终能不能转出来”，而是观察声音按真实时间进入时，系统何时开始出字、文字何时稳定、期间改写多少，以及 final 有多准确。

协议分成两条场景轨道：

### A. 语音输入法

- 短到中等长度的单人连续口述；
- 关注开口后的即时反馈、partial 稳定性和停顿后的 final；
- 主要报告首字延迟、稳定延迟、改写率和 final CER/MER；
- 不用长会议平均值代替输入法体验。

### B. 线下会议字幕

- 会议现场的连续语音字幕，不是会后离线转写；
- 允许更长会话、自然停顿和多人轮换，样本是否含重叠必须单独标注；
- 关注持续输出、分段 final、字幕稳定性、断流/重连和 final CER/MER；
- 发言人识别若评测，应作为独立维度，不能混入实时 ASR 总分。

两条轨道分别选样、分别排名。只有某系统完成对应轨道，才进入该轨道比较。

## 2. 公平的实时输入

### 2.1 预录音频 1× 回放

使用冻结的预录音频，按音频本身的时间速度 **1× replay**。这样每套系统听到完全相同的声音，同时保留真实的逐帧等待。

- 回放时钟使用单调时钟；`t=0` 为开始发送第一帧的时刻。
- 不允许整段文件先上传、解码完再伪装成流式结果。
- 不允许快于 1× 发送；调度误差、阻塞和重连必须记录。
- 网络商业 API 记录客户端发送与接收时间；不能用服务端自报延迟替代端到端延迟。
- 每次回放前重新建立独立会话，不复用上一轮识别上下文。

1× 回放只是把可复现音频送入实时接口，并不声称它覆盖真人麦克风、现场声学设备或网络抖动的全部影响。真人交互测试可后续单列，不与本协议混算。

### 2.2 20 ms canonical chunk

canonical 输入为冻结音频的连续 **20 ms chunk**，推荐 16 kHz、单声道、PCM signed 16-bit little-endian。最后不足 20 ms 的尾帧保留，并记录真实样本数。

- chunk 必须连续、不重叠、不丢样本，按顺序发送。
- 每帧记录序号、音频起止时间、计划发送时间和实际发送时间。
- 若商业接口要求不同编码或一次合并多帧，adapter 可以转换或 coalesce，但 `_machine/` 必须记录转换、聚合帧数和实际调用节奏。
- adapter 的缓冲时间计入端到端延迟，不能从指标中扣除。
- 若接口不能接受逐步输入，它不属于实时轨道，应记为 `N/A`，不能通过外部切窗包装获得“原生实时”名次。

## 3. partial 与 final

每条接收事件必须保存本地单调接收时间、provider 事件类型、原始文本和规范化文本。

- **partial**：会话尚未提交、之后允许被扩写或改写的中间假设。
- **final**：系统明确提交的不可再改分段结果；如果接口没有 final 标志，只能按预注册的会话结束规则派生，并注明 `derived final`。
- 系统只返回 final、不返回 partial 时，partial 能力记为不支持；不能复制 final 制造 partial。
- 系统发送空事件、心跳或标点占位时，不算首字。
- 断流、超时、空 final、重复 final 和 final 后改写都要作为事件保留并单独计数。

人读版 partial 时间线写入 `outputs/<system-id>/partials.tsv`；完整原始事件只写入 `_machine/runs/.../events.jsonl`。

## 4. 指标定义

所有延迟以客户端单调时钟计算，单位为毫秒。reference 的语音起点和文字必须由人工确认；无法可靠对齐时，不发布依赖该边界的延迟数字。

### 4.1 首字延迟

从人工标注的首段语音起点，到客户端收到第一条包含非空可见文字的 partial 或 final 的时间：

`首字延迟 = first_text_received - reference_speech_onset`

同时标明首条文字来自 partial 还是 final。首字是否正确另行报告，不能用一个很快但错误的字符掩盖体验。

### 4.2 稳定延迟

某个 reference 字符或 MER token 第一次出现在正确位置，且后续 partial/final 不再将其删除、替换或移位的时刻，减去该内容对应的人工语音结束时间。

- 报告 token 级 P50、P90 和整段 final 稳定延迟；
- 未提供 partial 的系统只能以 final 作为稳定时刻，并注明 `final-only`；
- 尚无可靠 token 时间边界时，只报告整段 final 延迟，不虚构 token 稳定延迟。

### 4.3 改写率

改写只计算对既有假设的撤回或替换，纯粹在末尾追加新文字不算改写。对相邻规范化假设计算编辑脚本：

`改写字符数 = max(0, ED(h[i-1], h[i]) - max(0, len(h[i]) - len(h[i-1])))`

`改写率 = Σ改写字符数 / max(1, final 规范化长度)`

同时报告 partial 事件数，避免“几乎不发 partial”仅凭低改写率显得更好。final-only 系统改写率记为 `N/A`，不是 0。

### 4.4 最终准确率 CER / MER

- 中文为主的样本报告 final **CER**；
- 中英混合样本同时报告 **MER**，中文按字、英文按归一化词计数；
- 使用冻结的文本归一化、标点和数字规则，reference 与 hypothesis 完全同口径；
- 只给 final 计准确率，partial 不混入 CER/MER；
- 删除、插入、替换数和 reference 单位数必须与比率一起发布。

准确率、延迟、改写率、失败率分别报告，不合成总分。

## 5. 三次独立重复

每个“样本 × 系统”执行 **3 次** 1× replay：

- 音频、20 ms chunk、adapter 配置、文本规则和超时保持一致；
- 每轮使用新会话和唯一 repeat ID；
- 三次都保留，失败或超时不能静默丢弃或补跑后替换；
- 人读报告列出三次原值，并给中位数与范围；只有 3 次时不把 P90 当成稳定总体估计；
- 系统执行顺序应轮换，并记录本地负载、网络条件、区域和商业 API 版本。

若系统版本、接口参数或 adapter 代码变化，必须生成新的 run 版本，不能与旧重复混为一组。

## 6. 系统分轨

| 轨道 | 系统 | Phase 2 状态与边界 |
|---|---|---|
| 本地开放模型 | Qwen3-ASR 0.6B | 待验证真实逐步输入和 partial/final 事件；通过前不填结果 |
| 本地开放模型 | Qwen3-ASR 1.7B | 与 0.6B 使用相同样本和 adapter 协议，独立报告算力与延迟 |
| 商业原生实时 API | 待登记具体服务与版本 | 只使用供应商实时接口；记录网络、区域、计费和数据处理边界 |
| N/A | MOSS-Transcribe-Diarize 0.9B | 本阶段没有纳入可验证的原生实时 partial/final 接口，记 `N/A` |

MOSS 的离线长音频、时间戳和发言人能力继续留在既有离线评测，不因 Phase 2 的 `N/A` 被解释为转录质量差。若未来增加外部分窗或封装服务，必须建立“外接实时管线”新轨道，不能回填成模型原生能力。

Qwen 0.6B、Qwen 1.7B 与商业 API 即使使用同一音频，也先在各自部署轨道内报告：本地模型要披露硬件、峰值资源和 adapter；商业 API 要披露网络、价格、地域和隐私边界。需要做跨轨比较时，只能引用同一协议下的共同指标，并继续保留这些部署差异。

## 7. 每轮执行与产物

1. 在 `SAMPLE_STATUS.md` 登记真实样本，冻结 audio、reference 和 SHA。
2. 预注册系统版本、adapter、超时、endpointing 和文本规范化规则。
3. 对每套系统执行三次 1× replay，保存完整发送/接收事件。
4. 从冻结事件派生人读 transcript、partials、captions 和指标。
5. 校验三次运行与 SHA 后，写样本级 `COMPARISON.md`。

JSON、JSONL、请求、响应、事件和机器指标只写入 `_machine/`。任何系统结果缺失时明确写“未运行”“失败”或 `N/A`，不得用示例数字填充。

