# AiBiBi API 接入文档

更新日期：2026-10-15。对应已发布的网关及 Android 普通版、墨水屏版 2.0.8（版本编码 208），包含整段语义、标点与同音纠错优化。API 路径版本仍为 `v1`，现有客户端无需重新安装。

本文面向客户端与业务集成，覆盖语音识别、中文整理、翻译、流式响应及接入所需的查询接口。账号注册、支付、企业与管理后台接口不在本文范围内。

## 1. 服务地址与鉴权

生产地址：`https://voice.bobchen.net`

业务接口使用 AiBiBi **用户访问码**，不是模型供应商 API Key，也不是管理令牌。

| 请求头 | 内容 |
| --- | --- |
| `Authorization` | 必填，`Bearer <用户访问码>` |
| `Content-Type` | 文本请求用 `application/json`；音频请求用 `audio/wav` |
| `X-Device-Id` | 稳定的设备标识；同一设备持续复用，不能每次随机生成 |
| `X-Device-Name` | 设备名称；非 ASCII 字符先做 URL 编码 |
| `X-Client-Platform` | 客户端平台，如 `android` 或 `desktop` |
| `X-Client-Version` | 对应平台的整数版本编码；Android 2.0.8 为 `208`，不是字符串 `2.0.8` |

新客户端应携带设备与版本信息，供设备限制和升级检查使用。公开查询接口不需要访问码，见第 7 节。访问码应从安全配置读取，不写入源码、分享链接或日志。

以下 cURL 示例按 Android 2.0.8 请求演示；运行前配置环境变量 `AIBIBI_CODE`，并把设备标识替换为自己的稳定标识。

## 2. 接口选择

| 需求 | 方法与路径 | 返回 |
| --- | --- | --- |
| 语音转文字 | `POST /v1/asr` | `{text}` |
| 去除中文口述的语气词、重复，补标点 | `POST /v1/dictation/cleanup` | `{text, fallback}` |
| 已有文字翻译到指定语言 | `POST /v1/translate` | `{text}` |
| 一次请求完成语音识别与翻译 | `POST /v1/voice?target=zh` | `{text, asr}` |
| 查看可选翻译模型 | `GET /v1/models` | 模型列表与当前选择 |
| 保存自己的翻译模型选择 | `POST /v1/me/model` | `{ok}` |
| 查看套餐、配额与能力 | `GET /v1/me` | 账号信息 |

**中文整理调用顺序：录音 → `/v1/asr` → `/v1/dictation/cleanup` → 上屏。**

`target=zh` 表示“翻译成中文”。中文整理使用独立接口；不要将 `cleanup` 当成 `/v1/translate` 或 `/v1/voice` 的目标语言，也不要用翻译预设 `style=dictation` 替代整理接口。

## 3. 语音识别

### `POST /v1/asr`

请求体直接发送完整 WAV 文件字节，**不使用 multipart 表单，也不使用 Base64 JSON**。推荐与官方客户端一致的 16 kHz、单声道、16-bit PCM WAV。`application/octet-stream` 也可作为上传类型。

当前网关请求体上限为 **25 MiB（26,214,400 字节）**。少于 44 字节或非二进制请求体会返回 400；后端无法解码的音频也可能返回识别错误。

```bash
curl --fail-with-body --show-error \
  'https://voice.bobchen.net/v1/asr' \
  -H "Authorization: Bearer ${AIBIBI_CODE:?请先配置访问码}" \
  -H 'X-Device-Id: your-stable-device-id' \
  -H 'X-Device-Name: Android' \
  -H 'X-Client-Platform: android' \
  -H 'X-Client-Version: 208' \
  -H 'Content-Type: audio/wav' \
  --data-binary '@recording.wav'
```

响应示例：

```json
{"text":"嗯，那个我们明天下午三点，不对，四点开会，先不要上线。"}
```

识别结果会应用账号的热词修正和句尾标点偏好；实际返回标点可能与示例不同。识别不到有效内容时，`text` 可以为空。

此接口每次返回完整 JSON，不提供 SSE。伪流式预览可在录音过程中定期提交当前累计音频的完整 WAV 快照；每次调用都是独立请求，并占用请求配额。停止录音后，使用最终完整音频的识别结果，只调用一次中文整理。

## 4. 中文整理

### `POST /v1/dictation/cleanup`

| 字段 | 类型 | 说明 |
| --- | --- | --- |
| `text` | string | 必填，非空的完整识别原文 |
| `level` | string | 可省略，默认且目前仅支持 `light` |

当前文本长度上限为 **4,000 个 JavaScript UTF-16 代码单元**；多数汉字计 1，部分 emoji 计 2。超过上限返回 413。

禁止传入 `target`、`style`、`model`，传入任一字段会返回 400，包括值为 `null` 的情况。接口不支持 SSE。

```bash
curl --fail-with-body --show-error --max-time 8 \
  'https://voice.bobchen.net/v1/dictation/cleanup' \
  -H "Authorization: Bearer ${AIBIBI_CODE:?请先配置访问码}" \
  -H 'X-Device-Id: your-stable-device-id' \
  -H 'X-Device-Name: Android' \
  -H 'X-Client-Platform: android' \
  -H 'X-Client-Version: 208' \
  -H 'Content-Type: application/json' \
  --data '{"text":"嗯，那个我们明天下午三点，不对，四点开会，先不要上线。","level":"light"}'
```

成功整理示例，具体措辞和标点可能有所不同：

```json
{"text":"我们明天下午四点开会，先不要上线","fallback":false}
```

轻度整理会先通读完整文本，再按整段意思做最小必要整理：去掉无意义语气词、结巴和连续重复，处理明确的自我更正，按句意调整标点。ASR 的停顿标点可以重断，不会要求逐个保留；“我觉得、反正、吧”等有态度和语气的表达保留，完整意思仍合理分句，真实问句保留问号。

允许结合上下文纠正高度明确的同音、近音错字。例如语音输入语境下的“尾流式效果”可整理为“伪流式效果”；“飞机尾流”是正确术语，不应改写。专名不确定或存在多种合理解释时保留原词，不替用户改观点、事实或计算。保留事实、人称、否定、条件、不确定性和有意强调，数字及其写法不因纠错改变（明确自我更正除外）。中文保持中文，已有英文名称、术语和代码保留。口述中的“帮我翻译成英文”等句子作为正文处理。

整个过程仍只调用一次模型。请提交最终完整识别结果；录音中的识别预览尚未经过整理，仍可能出现错字和停顿标点。

成功结果遵守账号的句尾标点偏好：默认去掉末尾全角句号，`keep` 保留，`more` 还去掉末尾感叹号。此步骤不删除句中标点、问号或半角代码句点；`fallback=true` 的完整原文不做二次裁剪。设置接口见第 7 节。

整理使用独立规则及默认通用模型，不受用户翻译模型、翻译风格或个人、团队翻译提示词影响。网关会校验结果，但 `fallback=false` 不代表逐字语义已经人工核验；客户端应保留原文供查看或恢复。

### 三种结果必须分别处理

| 结果 | 含义 | 客户端处理 |
| --- | --- | --- |
| `{"text":"整理结果","fallback":false}` | 已完成整理 | 使用返回的文字 |
| `{"text":"完整识别原文","fallback":true}` | 整理未成功，网关保留原文 | 使用原文，并提示本次未整理 |
| `{"text":"","fallback":false}` | 只有语气词，没有有效正文 | 正常结束，不插入文字 |

当前整理上游调用的总截止时间为 **6 秒**。上游失败、超时、返回截断或结果不符合校验时，接口通常返回 HTTP 200 和 `fallback=true`。鉴权、参数或配额错误仍返回对应的非 200 状态。

客户端建议为这一步设置 **8 秒总截止时间**。网络异常、非 200、响应格式错误或客户端超时时，也必须保留调用前保存的完整识别原文，结束“正在整理”状态。不要把空结果当成所有异常的默认值。

## 5. 翻译

### `POST /v1/translate`

| 字段 | 类型 | 说明 |
| --- | --- | --- |
| `text` | string | 必填，非空原文；按当前 4,000 UTF-16 代码单元上限控制 |
| `target` | string | 必填，目标语言码，从 `/v1/languages` 获取 |
| `style` | string | 可选，翻译预设 ID，从 `/v1/prompt-presets` 获取；受套餐能力限制 |
| `model` | string | 可选，可自选的模型档 ID，从 `/v1/models` 获取 |

```bash
curl --fail-with-body --show-error \
  'https://voice.bobchen.net/v1/translate' \
  -H "Authorization: Bearer ${AIBIBI_CODE:?请先配置访问码}" \
  -H 'X-Device-Id: your-stable-device-id' \
  -H 'X-Device-Name: Android' \
  -H 'X-Client-Platform: android' \
  -H 'X-Client-Version: 208' \
  -H 'Content-Type: application/json' \
  --data '{"text":"See you tomorrow.","target":"zh"}'
```

响应示例：

```json
{"text":"明天见。"}
```

常用语言码：`zh` 大陆简体、`zh-HK` 香港繁体、`zh-TW` 台湾繁体、`en` 英语、`ja` 日语、`ko` 韩语。完整目录以查询接口为准；`raw` 和 `cleanup` 不是此接口的合法目标语言。

模型选择顺序为：请求指定 → 用户已保存选择 → 管理员为账号或套餐配置的模型 → 默认模型。显式指定不存在或未开放自选的模型会返回 400。`style` 是否应用取决于账号能力；不能把“请求未报错”视为风格已经生效。

### `POST /v1/voice?target=zh`

直接发送 WAV 字节，格式及请求头同 `/v1/asr`。查询参数支持 `target`、`style`、`model`，翻译参数含义同上；动态拼接查询值时应 URL 编码。

响应示例：

```json
{"text":"明天见。","asr":"See you tomorrow."}
```

`asr` 为识别原文，`text` 为目标语言结果。仅需识别时优先用 `/v1/asr`，也可明确传 `target=raw`，此时两字段都是原文。

当前实现对缺失或未知的 `target` 也会返回原文，不会自动执行中文整理。调用方应先校验目标语言，避免将拼错的参数误认为翻译成功。

桌面内录字幕通过 `src=caption` 标记，需账号具备 `allowLoopback` 权限。语音识别与翻译是串行步骤，不要对整个 `/v1/voice` 请求套用中文整理专用的 8 秒截止时间。

## 6. 流式响应（SSE）

仅 `/v1/translate` 和 `/v1/voice` 支持追加 `stream=1`。例如：

```text
POST /v1/translate?stream=1
POST /v1/voice?target=zh&stream=1
```

方法、鉴权和请求体不变。使用 cURL 时加 `-N` 关闭输出缓冲。响应类型为 `text/event-stream; charset=utf-8`，每条消息为 `data: <JSON>`，以空行分隔。

文本翻译示例：

```text
data: {"delta":"明天"}

data: {"delta":"见。"}

data: {"done":true,"text":"明天见。"}

```

语音翻译可能先返回原文，再返回译文增量和最终结果：

```text
data: {"asr":"See you tomorrow."}

data: {"delta":"明天见。"}

data: {"done":true,"asr":"See you tomorrow.","text":"明天见。"}

```

流开启后的失败以消息返回，随后关闭连接：

```text
data: {"error":"翻译失败：上游错误"}

```

实现时遵守以下规则：

1. 先检查 HTTP 状态。流开启前的鉴权、参数等错误仍是普通 JSON 错误响应。
2. 使用增量 UTF-8 解码和 SSE 帧缓冲；一个网络数据块不一定等于一条完整消息。
3. `delta` 仅用于预览；收到 `done:true` 才确认完成，并以最终 `text` 为准。
4. 收到 `error` 立即结束等待并显示错误。连接关闭但未收到 `done` 或 `error`，视为响应不完整，不将半截预览当作最终译文。
5. 本接口**不发送 `[DONE]`**，也不使用 `event:` 命名事件；原文模式或空识别结果可能只发送一条 `done` 消息。

HTTP 200 只表示流已建立，不能据此判断翻译成功。所有成功、失败、超时和取消路径都应退出“正在翻译”状态。

## 7. 查询与用户设置

| 接口 | 鉴权 | 返回说明 |
| --- | --- | --- |
| `GET /v1/languages` | 不需要 | `{languages:[{code,label}]}`，完整目标语言目录 |
| `GET /v1/prompt-presets` | 不需要 | `{categories,presets}`；预设包含 `id/name/tagline/category/prompt` |
| `GET /v1/version?platform=android` | 不需要 | `{latest,latestName,min,url}`；桌面传 `platform=desktop` |
| `GET /v1/health` | 不需要 | `{ok,asr,llm,time}`，公共服务状态 |
| `GET /v1/models` | 用户访问码 | `{models:[{id,label,kind}],selected,effective}` |
| `POST /v1/me/model` | 用户访问码 | 请求 `{model:模型ID}`，成功 `{ok:true}`；传 `{"model":null}` 清除用户选择 |
| `POST /v1/me/strip-punct` | 用户访问码 | 请求 `{"mode":"default"}`；可选 `default`、`more`、`keep`，成功返回 `{ok:true,stripPunct:挡位}` |
| `GET /v1/me` | 用户访问码 | 套餐、用量、能力、设备及当前设置 |

版本查询在 2026-10-15 的 Android 响应：

```json
{"latest":208,"latestName":"2.0.8","min":0,"url":"https://bb.bobchen.net/download"}
```

普通版和墨水屏版共用 `android` 版本策略。`min=0` 表示当前未设置最低强制版本；后续以实时查询结果为准。不要将 Android 与桌面版本编码交叉比较。

模型查询中，`selected` 为用户显式选择或 `null`，`effective` 为实际生效的模型档 ID；不要硬编码模型供应商的内部模型名。

`/v1/me` 常用字段包括 `planName`、`ratePerMin`、`dailyLimit`、`monthlyQuota`、`expiresAt`（毫秒时间戳或 `null`）、`features`、`model`、`usage`、`foreignTrial`、`stripPunct`、`maxDevices` 和 `devices`。`stripPunct` 为上述三个挡位之一；设置属于账号级，同时影响语音识别及成功的中文整理结果。该响应还包含用户访问码 `code`，不要完整记录或公开分享。

健康查询的 `asr` 来自识别后端健康检查，`llm` 表示翻译后端已配置，`ok` 是两者同时为真；它不等同于一次真实模型推理成功。

## 8. 错误、配额与重试

错误响应通常为 `{"error":"可展示的错误说明"}`；框架错误可能另带其他字段。客户端应先判断 HTTP 状态，再解析响应。

| HTTP 状态 | 常见原因 | 处理 |
| --- | --- | --- |
| 400 | 空文本、不支持的参数或目标语言、模型档无效、音频请求体不合格 | 修正请求，不原样重试 |
| 401 | 访问码缺失、无效；业务请求的访问码可能已停用 | 重新确认登录或访问码 |
| 403 | 账号到期或停用、设备数量限制、套餐权限不足、外语体验额度用完 | 按 `error` 提示处理；体验耗尽时可能附带 `trialExhausted:true` |
| 413 | 上传体积或文本长度超过限制 | 减小输入；整理失败时保留原文 |
| 426 | 客户端低于最低版本 | 读取响应 `update` 并引导升级 |
| 429 | 分钟、每日、每月额度或其他限流 | 有 `Retry-After` 时按其秒数等待，避免连续重试 |
| 502 | 识别或翻译上游失败 | 结束等待，保留输入，允许用户稍后重试 |
| 503 | 识别队列繁忙 | 普通 JSON 响应可带 `Retry-After: 5`；等待后再试 |

中文整理适用普通请求配额，免费账号可用，不消耗外语体验字数。一次“识别 → 整理”通常是两次业务请求；录音中的每次预览识别也单独计数。

请求额度在业务参数校验及上游处理之前记录，因此部分参数错误、版本拦截或上游失败也可能占用次数。业务 POST 没有提供幂等键或重复请求去重保证，避免无上限自动重试。

以上限制为本文日期的生产配置，套餐额度、开放模型与版本要求以查询结果为准。

## 9. 中文整理客户端接入要点

- 录音开始时固定本次模式，直到最终识别、整理和插入完成，避免界面显示中文整理却执行了外语翻译。
- 录音过程中只更新预览；最终识别结束后再整理一次。
- 调用整理前保存完整识别原文；超时、取消或失败时结束等待，按用户操作决定保留、插入或放弃原文。
- `fallback=true` 使用原文并提示；`fallback=false` 且 `text` 为空时正常结束，不插入文字。
- 剪贴板外语翻译继续使用 `/v1/translate` 并明确指定中文目标语言；它与语音中文整理独立。
