本文介绍通过WebSocket进行工业生产指令转写的方法。
前提条件
已开通服务并获取与配置 API Key,请配置API Key到环境变量,而非硬编码在代码中,防范因代码泄露导致的安全风险。
调用时序图

WebSocket建联
对应时序图中过程1。
对于常用编程语言,有许多现成的WebSocket库和示例可供参考,例如:
- Go:
gorilla/websocket - PHP:
Ratchet - Node.js:
ws
建联请求头
WebSocket接入地址
向服务端发送指令
您可以向服务端发送指令,控制转写的开始和停止。
指令分为两种,run-task和finish-task,都需要以Text Frame方式发送的JSON格式的数据,具体协议如下:
run-task指令
对应时序图中过程2,通知服务端开始一个转写任务。
协议字段如下:
字段 | 类型 | 说明 |
|---|---|---|
header | Object | |
header.action | String | 固定填写run-task。 |
header.task_id | String | 自定义16位随机字符串,排查问题使用,后续finish-task也应该使用这个task_id。 |
header.streaming | String | 固定填写duplex。 |
payload | Object | |
payload.model | String | 固定填写tingwu-industrial-instruction。 |
payload.task_group | String | 固定填写aigc。 |
payload.task | String | 固定填写multimodal-generation。 |
payload.function | String | 固定填写generation。 |
payload.input | Object | |
payload.input.appId | String | 填写工业指令转写控制台中的应用id,可从控制台获取。 |
payload.input.directive | String | 固定传start。 |
payload.parameters | Object | |
payload.parameters.sampleRate | Integer | 音频采样率,目前只支持16000。 |
payload.parameters.format | String | 设置待识别音频格式。支持的音频格式:pcm、wav、mp3、opus、speex、aac、amr。对于opus和speex格式的音频,需要ogg封装;对于wav格式的音频,需要pcm编码。 |
payload.parameters.maxEndSilence | Integer | 最大静音时长,单位ms,在出字后检测到超过此时长则会认为一句话结束,取值范围为[0, 6000]。 非必传,默认值为1500。 |
payload.parameters.terminology | String | 转写指令集id,可从控制台获取。 |
finish-task
对应时序图中过程5,通知服务端音频已全部发送完成,录音已结束。
协议字段如下:
字段 | 类型 | 说明 |
|---|---|---|
header | Object | |
header.action | String | 固定填写finish-task。 |
header.task_id | String | 请填写run-task指令中填写的task_id。 |
header.streaming | String | 固定填写duplex。 |
payload | Object | |
payload.model | String | 固定填写tingwu-industrial-instruction。 |
payload.task_group | String | 固定填写aigc。 |
payload.task | String | 固定填写multimodal-generation。 |
payload.function | String | 固定填写generation。 |
payload.input | Object | |
payload.input.directive | String | 固定传stop。 |
向服务端发送音频
将原始音频直接转为二进制流即可,无需额外处理。但需要注意:
- 上传的语音识别音频采样率必须是16000Hz。
- 音频编码格式需要与run-task中填写的一致。
- 支持的音频格式:pcm、wav、mp3、opus、speex、aac、amr。对于opus和speex格式的音频,需要ogg封装;对于wav格式的音频,需要pcm编码。
接收服务端返回的事件
在指令或音频发送后,服务端会向您发送不同种类的事件,每个事件代表不同的处理阶段,请严格遵循时序图对不同事件做相应处理。
事件总共分为四种,分别是speech-listen事件、recognize-result事件、ai-result事件及speech-end事件。
speech-listen事件
对应时序图中的过程3,speech-listen事件会在run-task指令后返回,代表服务端收到了您的转写指令,并完成相关初始化工作,您可以开始发送音频了。
协议字段如下:
字段 | 类型 | 说明 |
|---|---|---|
header | Object | |
header.event | String | 固定为result-generated。 |
header.task_id | String | 您在run-task指令中填写的task_id。 |
payload | Object | |
payload.output | Object | |
payload.output.action | String | 固定为speech-listen。 |
payload.output.dataId | String | 您本次转写的任务id,您可以通过该id向我们反馈问题,同时在账单中也可以通过该id查看对应任务的计费项。 |
recognize-result事件
对应时序图中的过程4,recognize-result事件会在您发送一段时间的音频后返回,也可能会在您发送finish-task指令后返回,代表当前服务端识别到的原文和译文结果。
协议字段如下:
字段 | 类型 | 说明 |
|---|---|---|
header | Object | |
header.event | String | 固定为result-generated。 |
header.task_id | String | 您在run-task指令中填写的task_id。 |
payload | Object | |
payload.output | Object | |
payload.output.action | String | 固定为recognize-result。 |
payload.output.transcription | Object | 转写的原始结果。 |
payload.output.transcription.sentenceId | Integer | 句子序号。 |
payload.output.transcription.beginTime | Integer | 当前句子已识别部分的第一个字在音频中的开始时间,单位ms。 |
payload.output.transcription.endTime | Integer | 当前句子已识别部分的最后一个字在音频中的结束时间,单位ms。 |
payload.output.transcription.sentenceEnd | Boolean | 当前句子是否已结束。 |
payload.output.transcription.text | String | 当前句子已识别部分的内容。 |
payload.output.transcription.words | List[Word] | 句子分词信息。 |
payload.output.translations | Object | 转写的翻译结果。 |
payload.output.translations.sentenceEnd | Boolean | 当前句子是否结束。 |
payload.output.translations.translations | Object | 转写的翻译目标语种结果集合。 |
payload.output.translations.translations.zh | Object | 目前只支持翻译成中文,所以只会有zh一个对象。 |
payload.output.translations.translations.zh.lang | String | 固定为zh。 |
payload.output.translations.translations.zh.sentenceId | Integer | 句子序号。 |
payload.output.translations.translations.zh.beginTime | Integer | 当前句子已翻译部分的第一个字在音频中的开始时间,单位ms。 |
payload.output.translations.translations.zh.endTime | Integer | 当前句子已翻译部分的最后一个字在音频中的结束时间,单位ms。 |
payload.output.translations.translations.zh.sentenceEnd | Boolean | 当前句子是否已结束。 |
payload.output.translations.translations.zh.text | String | 当前句子已翻译部分的内容。 |
payload.output.translations.translations.zh.words | List[Word] | 已翻译句子分词信息。 |
字段 | 类型 | 说明 |
|---|---|---|
beginTime | Integer | 当前词在音频中的开始时间。 |
endTime | Integer | 当前词在音频中的结束时间。 |
text | String | 当前词的内容。 |
ai-result事件
对应时序图中的过程6。ai-result事件会在最后一条recognize-result事件后返回给您,代表工业指令转写结合指令集纠正后的最终结果。
协议字段如下:
字段 | 类型 | 说明 |
|---|---|---|
header | Object | |
header.event | String | 固定为result-generated。 |
header.task_id | String | 您在run-task指令中填写的task_id。 |
payload | Object | |
payload.output | Object | |
payload.output.action | String | 固定为ai-result。 |
payload.output.aiResult | Object | |
payload.output.aiResult.correction | String | 工业指令转写最终结果 |
speech-end事件
对应时序图中的过程7。speech-end事件会在ai-result事件后发送给您,代表工业指令转写完全结束,之后您可以关闭WebSocket连接。
协议字段如下:
字段 | 类型 | 说明 |
|---|---|---|
header | Object | |
header.event | String | 固定为result-generated。 |
header.task_id | String | 您在run-task指令中填写的task_id。 |
payload | Object | |
payload.output | Object | |
payload.output.action | String | 固定为speech-end。 |
task-failed事件
若在任务过程中,由于客户端传参错误或服务端内部错误导致任务失败,服务端会返回给您task-failed事件,随即会中断WebSocket连接。
协议字段如下:
字段 | 类型 | 说明 |
|---|---|---|
header | Object | |
header.event | String | 固定为result-generated。 |
header.task_id | String | 您在run-task指令中填写的task_id。 |
payload | Object | |
payload.output | Object | |
payload.output.action | String | 固定为task-failed。 |
payload.output.errorCode | String | 错误码 |
payload.output.errorMessage | String | 错误信息 |
WebSocket连接复用
本功能不支持连接复用,请在创建任务时新建WebSocket连接。
若连接15s内无文本消息或二进制消息发送,连接将自动断开。
代码示例
错误码
错误码 | 错误信息 | 说明 |
|---|---|---|
InvalidParameter | Invalid parameter. Please refer to the official documents. | 参数错误,请检查您传入的参数。 |
InvalidParameter | MaxEndSilence invalid, must between [0. 6000]. | 传入的maxEndSilence参数不合法。 |
InvalidParameter | Terminology not exist. | 传入的指令集不存在。 |
InvalidParameter | SampleRate invalid. | 传入的采样率参数不合法。 |
InvalidParameter | Audio format invalid. | 传入的音频编码格式参数不合法。 |
InvalidParameter | Terminology invalid. | 传入的指令集Id不合法。 |
Agent.FrameSequenceIllegal | Agent Websocket Frame Sequence Illegal. | 调用指令时序不合法。 |
Agent.InputActionIllegal | Agent Input Action Illegal. | 传入的指令action字段不合法。 |
Agent.InputAppIdIllegal | Agent Input appId illegal. | 传入的应用Id字段不合法。 |
Agent.AppNotPublished | Agent App not published. | 传入的应用Id尚未发布。 |
Agent.CustomTaskIdInvalid | The length of custom task id must be 16. | 传入的taskId字段长度不合法。 |
BIL.ServiceNotActivate | User hasn't activate service. | 您尚未开通听悟Agent服务。 |
BIL.UserArrears | User is in arrears. | 您目前处在欠费状态。 |
Agent.AppInfoNotExist | Agent App Info not exist. | 传入的应用Id信息不存在,请先在控制台保存并发布应用配置信息。 |
ServerError | Server error. | 服务端内部错误。 |