监听器与回调数据
监听器与回调数据
TmkTranslationListener
public protocol TmkTranslationListener: AnyObject {
func onRecognized(from engine: AbstractChannelEngine, result: TmkResult<String>, isFinal: Bool)
func onTranslate(from engine: AbstractChannelEngine, result: TmkResult<String>, isFinal: Bool)
func onAudioDataReceive(from engine: AbstractChannelEngine, result: TmkResult<String>, data: Data, channelCount: Int)
func onError(_ error: TmkTranslationError)
func onError(code: Int, message: String)
func onEvent(name: String, args: Any?)
func onStateChanged(from engine: AbstractChannelEngine, snapshot: TmkTranslationChannelStateSnapshot)
}
回调线程:
TmkTranslationListener的所有回调都会在主线程回调。
各回调说明:
onRecognized(...)
-
识别结果回调。
-
result.data:识别文本。 -
isFinal可能取值:-
false:增量识别结果,后续还可能继续回调。 -
true:本段识别最终结果。
-
-
result.isLast:当前结果对象中的结束标记,通常与isFinal含义保持一致。 -
result.srcCode/result.dstCode:当前通道的源语言与目标语言代码。 -
result.extraData字段与可能取值(按当前 SDK 实现):
| key | 类型 | 可能取值/说明 | 出现场景 |
|---|---|---|---|
trace_id | String | 链路追踪 ID;未启用 trace 时可能不存在 | 在线/离线 |
bubble_id | String | 文本气泡 ID;在线来自服务端,离线由 SDK 独立生成 | 在线/离线 |
chunk_id | String | 文本分片 ID;在线来自服务端,离线由 SDK 生成 | 在线/离线 |
channel | String | 常见:left、right、1(离线收听) | 在线/离线 |
kind | String | origin | 离线 |
state | String | partial、completed | 离线 |
text | String | 当前识别文本(通常与 result.data 一致) | 离线 |
offset | Int64 | 本段 ASR 语音在音频流中的起始偏移(纳秒);服务端未下发时不存在 | 在线/离线 |
duration | Int64 | 本段 ASR 语音时长(纳秒);服务端未下发时不存在 | 在线/离线 |
extraData 字段按事件和模式动态出现,不保证全部存在。offset/duration 仅 ASR 识别回调携带,MT 翻译回调(onTranslate)不包含此字段。
onTranslate(...)
-
翻译结果回调。
-
result.data:翻译文本。 -
isFinal可能取值:-
false:增量翻译结果。 -
true:本段翻译最终结果。
-
-
result.extraData字段与可能取值(按当前 SDK 实现):
| key | 类型 | 可能取值/说明 | 出现场景 |
|---|---|---|---|
trace_id | String | 链路追踪 ID;未启用 trace 时可能不存在 | 在线/离线 |
bubble_id | String | 文本气泡 ID;在线来自服务端,离线由 SDK 独立生成 | 在线/离线 |
chunk_id | String | 文本分片 ID;在线来自服务端,离线由 SDK 生成 | 在线/离线 |
channel | String | 常见:left、right、1(离线收听) | 在线/离线 |
kind | String | translation | 离线 |
state | String | partial、completed | 离线 |
text | String | 当前翻译文本(通常与 result.data 一致) | 离线 |
extraData 字段按事件和模式动态出现,不保证全部存在。
onAudioDataReceive(...)
-
翻译后的 PCM 音频回调。
-
data:原始 PCM16LE 音频数据。 -
channelCount可能取值:-
1:单声道。 -
2:双声道。
-
-
result.data当前通常是描述性文本,不建议业务方依赖其固定内容。 -
result.extraData字段与可能取值(按当前 SDK 实现):
| key | 类型 | 可能取值/说明 | 出现场景 |
|---|---|---|---|
uid | UInt | 音频来源 UID | 在线 |
trace_id | String | 链路追踪 ID;未启用 trace 时可能不存在 | 离线 |
bubble_id | String | 文本气泡 ID;离线由 SDK 独立生成 | 离线 |
chunk_id | String | 文本分片 ID;离线由 SDK 生成 | 离线 |
channel | String | 1(离线收听)或 left/right(离线一对一) | 离线 |
onError(_:)
-
SDK 统一错误回调。
-
error.code:统一错误码。 -
error.category常见取值:caller、network、rtcRtm、audio、state、internal。 -
error.message:对外可读的错误描述。
onError(code:message:)
-
兼容旧接口的错误回调。
-
默认实现会由
onError(_:)自动桥接。
onEvent(name:args:)
-
通用事件回调。
-
name为事件名。 -
args通常为TmkResult<String>,也可能为nil。 -
当
args为TmkResult<String>时,可通过result.extraData获取事件扩展字段。
常见在线事件:
| 事件名 | 含义 | args 常见内容 |
|---|---|---|
online_stream_message_parsed | 在线识别/翻译流消息解析完成 | TmkResult<String> |
online_audio_metadata | 在线音频链路元数据事件 | TmkResult<String> 或 nil |
online_recognition_failure | 在线识别失败 | TmkResult<String> 或 nil |
online_notification | 在线通知事件 | TmkResult<String> 或 nil |
online_tts_state | 在线 TTS 状态变化,可用于播放高亮 | TmkResult<String> 或 nil |
online_bubble_end | 在线气泡结束态标记事件 | TmkResult<String>,data 为 bubble_end |
online_bubble_end 表示 SDK 收到服务端针对某个 bubble_id 下发的 bubble_end 事件。业务层可将对应 bubble 标记为结束态并更新展示样式;该事件不阻止后续同 bubble_id 的识别或翻译内容继续更新,也不改变 onRecognized / onTranslate 的 isFinal、isLast 语义。
online_tts_state 表示服务端下发的 TTS 播放状态。SDK 会把 session_id、chunk_id、bubble_id、is_end 等字段透传到 result.extraData:业务侧可用 session_id 高亮源文片段、用 chunk_id 高亮译文片段;is_end == true 时应取消对应高亮。高亮属于 App/Demo 展示逻辑,SDK 只负责透传事件和稳定字段。
在线事件 result.extraData 字段与可能取值:
| key | 类型 | 可能取值/说明 |
|---|---|---|
uid | UInt | 远端用户 UID |
stream_id | Int | Agora 流 ID |
event | String | translate_speech_to_speech、notification、recognition_failure、tts_playback_state 或其他服务端事件名 |
event_type | String | translateSpeechToSpeech、notification、recognitionFailure、ttsPlaybackState、unknown(...) |
kind | String | 常见:origin、translation |
trace_id | String | 链路追踪 ID |
channel | String | 常见:left、right |
locale | String | 语言代码,如 zh-CN、en-US |
text | String | 事件文本内容 |
state | String | 常见:partial、completed、failed、started |
is_end | Bool | true / false |
bubble_id | String | 文本气泡 ID;online_bubble_end 中用于标记对应气泡结束 |
session_id | String | 在线语音段 ID;online_tts_state 中可用于源文高亮 |
chunk_id | String | 在线翻译片段 ID;online_tts_state 中可用于译文高亮 |
metadata_size | Int | metadata 字节数(online_audio_metadata) |
payload_size | Int | 消息/metadata 字节数 |
tx_quality | Int | 上行网络质量(Agora 枚举值) |
rx_quality | Int | 下行网络质量(Agora 枚举值) |
audio_loss_rate | Int | 音频丢包率(百分比整数) |
常见离线事件:
| 事件名 | 含义 | args 常见内容 |
|---|---|---|
offline_stream_message_parsed | 离线识别/翻译事件 | TmkResult<String> |
offline_audio_metadata | 离线音频链路元数据事件 | TmkResult<String> 或 nil |
offline_recognition_failure | 离线识别失败 | TmkResult<String> 或 nil |
offline_notification | 离线通知事件 | TmkResult<String> 或 nil |
offline_tts_state | 离线 TTS 状态变化 | TmkResult<String> 或 nil |
offline_bubble_end | 离线气泡结束事件,与在线 online_bubble_end 语义对齐 | TmkResult<String>,可从 result.bubbleId 读取气泡 ID |
离线事件 result.extraData 字段与可能取值:
| key | 类型 | 可能取值/说明 |
|---|---|---|
trace_id | String | 链路追踪 ID;仅在 Demo 侧发送 trace 时存在 |
bubble_id | String | 文本气泡 ID;离线由 SDK 独立生成 |
chunk_id | String | 文本分片 ID;离线由 SDK 生成 |
channel | String | 收听:1;一对一:left / right |
event | String | translate_speech_to_speech、recognition_failure、notification、tts_playback_state |
kind | String | origin、translation(offline_stream_message_parsed) |
state | String | partial、completed、failed、started |
text | String | 事件文本或错误文本 |
locale | String | 语言代码(origin=源语言,translation=目标语言) |
stage | String | asr、translation、tts(失败通知事件) |
uid | UInt | 音频 metadata 对应 UID(offline_audio_metadata) |
metadata_size | Int | metadata 字节数 |
payload_size | Int | payload 字节数 |
onStateChanged(...)
-
通道状态变化回调。
-
推荐业务方监听该回调,用于展示“启动中 / 运行中 / 重连中 / 失败”等状态。
-
snapshot.state全量取值见下文TmkTranslationChannelState。 -
snapshot.reason全量取值见下文TmkTranslationChannelStateReason。 -
snapshot.code:当状态变化由错误触发时,可能包含错误码;否则为nil。 -
snapshot.isRecoverable:true表示 SDK 仍可能自动恢复,false表示通常需要业务方介入。
示例:
final class TranslationHandler: TmkTranslationListener {
func onRecognized(from engine: AbstractChannelEngine, result: TmkResult<String>, isFinal: Bool) {
print("识别: \(result.data), final=\(isFinal)")
}
func onTranslate(from engine: AbstractChannelEngine, result: TmkResult<String>, isFinal: Bool) {
print("翻译: \(result.data), final=\(isFinal)")
}
func onAudioDataReceive(from engine: AbstractChannelEngine,
result: TmkResult<String>,
data: Data,
channelCount: Int) {
print("audio bytes=\(data.count), channelCount=\(channelCount)")
}
func onError(_ error: TmkTranslationError) {
print("error=\(error.code) \(error.message)")
}
func onEvent(name: String, args: Any?) {
print("event=\(name)")
}
}
TmkResult<T>
public struct TmkResult<T> {
public let sessionId: Int
public let bubbleId: String
public let data: T
public let srcCode: String
public let dstCode: String
public let isLast: Bool
public let extraData: [String: Any]
}
字段说明:
-
sessionId-
会话 ID。
-
在线场景下一般对应 Agora uid 或会话维度标识。
-
离线场景由 SDK 生成,规则为毫秒级时间戳追加同毫秒内递增序号,降低同一时刻左右声道同时产出时的冲突概率。
-
-
bubbleId-
文本气泡 ID。
-
在线场景优先来自服务端
bubble_id。 -
离线场景由 SDK 按与
sessionId相同的毫秒级时间戳+序号规则独立生成,不等同于sessionId。
-
-
data-
结果主体。
-
文本结果里通常是
String。
-
-
srcCode- 源语言代码。
-
dstCode- 目标语言代码。
-
isLast- 是否是最后一条结果。
-
extraData-
附加信息字典。
-
chunk_id在线场景来自服务端;离线场景由 SDK 按毫秒级时间戳+序号规则生成,并与同一段 ASR/MT/TTS 结果保持一致。
-
extraData属于兼容型扩展字段。- 不同模式和不同事件的字段可能不同。
- 如无明确依赖,请不要强依赖某个未文档化 key;建议仅使用本节 11.1 中已列字段。
通道状态模型
TmkTranslationChannelState
public enum TmkTranslationChannelState: String {
case idle
case starting
case running
case reconnecting
case degraded
case stopping
case stopped
case failed
}
常见取值说明:
| 值 | 含义 |
|---|---|
idle | 初始状态,尚未启动 |
starting | 启动中 |
running | 运行中 |
reconnecting | 重连中 |
degraded | 已降级运行,通常仍可继续工作 |
stopping | 停止中 |
stopped | 已停止 |
failed | 已失败,通常需要业务方介入 |
TmkTranslationChannelStateReason
public enum TmkTranslationChannelStateReason: String {
case none
case startRequested
case started
case stopRequested
case stopped
case networkUnavailable
case networkRestored
case rtcConnecting
case rtcConnected
case rtcInterrupted
case rtcLost
case rtcKeepAliveTimeout
case rtcTokenRequested
case rtcTokenWillExpire
case sessionExpired
case invalidConfiguration
case permissionDenied
case bannedByServer
case serviceRejected
case messageChannelFailure
case engineError
}
常见取值说明:
| 值 | 含义 |
|---|---|
none | 无特殊原因 |
startRequested | 已收到启动请求 |
started | 启动完成 |
stopRequested | 已收到停止请求 |
stopped | 已停止 |
networkUnavailable | 网络不可用 |
networkRestored | 网络已恢复 |
rtcConnecting | 在线链路连接中 |
rtcConnected | 在线链路已连接 |
rtcInterrupted | 在线链路中断 |
rtcLost | 在线链路丢失 |
rtcKeepAliveTimeout | 在线保活超时 |
rtcTokenRequested | 正在请求 RTC token |
rtcTokenWillExpire | RTC token 即将过期 |
sessionExpired | 当前会话已过期 |
invalidConfiguration | 配置无效 |
permissionDenied | 权限不足 |
bannedByServer | 被服务端禁用 |
serviceRejected | 服务端拒绝请求 |
messageChannelFailure | 文本消息通道异常 |
engineError | 底层引擎异常 |
TmkTranslationChannelStateSnapshot
public struct TmkTranslationChannelStateSnapshot {
public let state: TmkTranslationChannelState
public let reason: TmkTranslationChannelStateReason
public let code: Int?
public let message: String
public let isRecoverable: Bool
public let updatedAt: Date
}
字段说明:
-
state- 当前状态。
-
reason- 状态变化原因。
-
code- 关联错误码,可能为空。
-
message- 补充说明文本。
-
isRecoverable- 是否可恢复。
-
updatedAt- 更新时间。
状态回调处理契约
App 应以 onStateChanged 作为通道 UI 状态的单一来源,不要自行把 starting 伪造为 running,也不要因单次弱网事件主动销毁通道。
| state | 常见 reason | App 推荐处理 |
|---|---|---|
idle | none | 显示待启动或初始化状态,不推流。 |
starting | startRequested / rtcConnecting / rtcConnected | 显示“通道连接中/正在加载”,禁止重复创建。rtcConnected 只表示媒体链路已连接,不代表完整业务链路已 ready。 |
running | started / rtcConnected / networkRestored | 显示通道可用,允许采集,清除弱网或重连提示。 |
degraded | networkUnavailable / messageChannelFailure / rtcTokenRequested / rtcTokenWillExpire | 显示非阻塞弱网或能力受损提示,不停止录音/播放,不弹 fatal 错误框。 |
reconnecting | networkUnavailable / rtcInterrupted / rtcLost / messageChannelFailure | 显示连接恢复中,禁止重复创建,等待 SDK 恢复或升级为失败。 |
stopping | stopRequested | 禁用操作按钮,等待停止完成。 |
stopped | stopped | 清理 UI 状态或离开页面。 |
failed | sessionExpired / invalidConfiguration / permissionDenied / bannedByServer / serviceRejected / rtcKeepAliveTimeout / engineError | 停止录音/播放,按错误码提示用户重新创建、重新初始化、下载模型、重新鉴权或离开。 |
离线通道不产生 rtcConnecting、rtcConnected、rtcInterrupted、rtcLost、rtcKeepAliveTimeout、messageChannelFailure 等 RTC/RTM 原因;离线 UI 仍消费同一套 state,但原因主要来自模型、pipeline 和离线鉴权状态。
事件回调处理契约
onEvent 用于诊断、弱提示和补充状态,不应替代 onRecognized、onTranslate、onAudioDataReceive 和 onStateChanged。
| 事件类型 | 常见事件 | App 推荐处理 |
|---|---|---|
| 在线运行事件 | online_started、online_stopped、online_runtime_state_changed | 日志和 UI 辅助;UI 状态以 onStateChanged 为准。 |
| 在线消息事件 | online_stream_message_raw、online_stream_message_parsed、online_notification、notification | 诊断为主;close_room 类通知需要停止当前会话引用,并提示用户重新创建或离开。 |
| 在线弱网事件 | online_network_quality、online_rtc_stats、online_remote_audio_stats、online_local_audio_stats | 连续采样后显示弱网提示,不直接释放通道。真正需要用户决策时等待 failed 状态或 onError。 |
| 在线远端离线事件 | online_remote_user_offline | 当 is_expected_service_uid=true 时,说明服务端音频/翻译订阅 uid 离线,对话不可继续,应提示重新创建或离开。 |
| 离线 pipeline 事件 | offline_pipeline_state、offline_stream_message_parsed、offline_audio_metadata | 诊断和日志为主;UI 仍以 onStateChanged 和业务结果回调为准。 |
| 离线结果辅助事件 | offline_asr_partial、offline_asr_final、offline_mt_partial、offline_mt_final、offline_tts_output、offline_tts_state、offline_recognition_failure | 可用于诊断或弱提示;正式文本和音频展示以识别、翻译、音频回调为准。 |
| 模型下载事件 | offline_model_cancelled、offline_model_update_required、下载进度、解压进度、模型包状态变化 | 更新模型列表和进度;取消不弹错误框,需更新时禁止直接启动离线通道。 |
离线模型包状态处理契约
| package state | App 推荐处理 |
|---|---|
ready | 显示已就绪;所有必需包 ready 后可创建离线通道。 |
needsDownload | 显示待下载,禁止启动离线通道。 |
needsUpdate | 显示需更新,引导重新下载。 |
resumable | 显示可续传,点击下载继续。 |
downloading | 显示下载进度,允许取消。 |
unzipping | 显示解压进度,避免重复触发下载。 |
failed | 显示失败,允许重试。 |
cancelled | 显示已取消,允许重新下载,不弹错误框。 |