This topic describes how to transcribe industrial production instructions using WebSocket.
Prerequisites
Activate the service and obtain and configure an API key. To prevent security risks from code leaks, configure the API key as an environment variable instead of hard coding it in your code.
Sequence diagram

Establish a WebSocketconnection
This corresponds to process 1 in the sequence diagram.
For common programming languages, many ready-to-use WebSocket libraries and examples are available, such as:
- Go:
gorilla/websocket - PHP:
Ratchet - Node.js:
ws
Connection request headers
WebSocketaccess URL
Send instructions to the server
You can send instructions to the server to start and stop transcription.
There are two types of instructions: run-task and finish-task. Both must be sent as JSON data in a text frame. The protocol is as follows:
run-task instruction
This corresponds to process 2 in the sequence diagram. It notifies the server to start a transcription task.
The protocol fields are as follows:
Field | Type | Description |
|---|---|---|
header | Object | |
header.action | String | Set to run-task. |
header.task_id | String | A custom 16-character random string used for troubleshooting. The subsequent finish-task must use the same task_id. |
header.streaming | String | Set to duplex. |
payload | Object | |
payload.model | String | Set to tingwu-industrial-instruction. |
payload.task_group | String | Set to aigc. |
payload.task | String | Set to multimodal-generation. |
payload.function | String | Set to generation. |
payload.input | Object | |
payload.input.appId | String | The application ID from the industrial instruction transcription console. You can obtain it from the console. |
payload.input.directive | String | Set to start. |
payload.parameters | Object | |
payload.parameters.sampleRate | Integer | The audio sample rate. Only 16000 is supported. |
payload.parameters.format | String | The format of the audio to be recognized. Supported formats: pcm, wav, mp3, opus, speex, aac, and amr. For opus and speex formats, Ogg encapsulation is required. For the wav format, PCM encoding is required. |
payload.parameters.maxEndSilence | Integer | The maximum duration of silence in milliseconds (ms). If silence longer than this duration is detected after text is generated, the sentence is considered complete. The value must be in the range of [0, 6000]. This parameter is optional. The default value is 1500. |
payload.parameters.terminology | String | The ID of the transcription instruction set. You can obtain it from the console. |
finish-task
This corresponds to process 5 in the sequence diagram. It notifies the server that all audio has been sent and the recording has ended.
The protocol fields are as follows:
Field | Type | Description |
|---|---|---|
header | Object | |
header.action | String | Set to finish-task. |
header.task_id | String | Enter the task_id specified in the run-task command. |
header.streaming | String | Set to duplex. |
payload | Object | |
payload.model | String | Set to tingwu-industrial-instruction. |
payload.task_group | String | Set to aigc. |
payload.task | String | Set to multimodal-generation. |
payload.function | String | Set to generation. |
payload.input | Object | |
payload.input.directive | String | Set to stop. |
Send audio to the server
Convert the raw audio directly into a binary stream without extra processing. Note the following:
- The sample rate of the uploaded audio for speech recognition must be 16000 Hz.
- The audio coding format must be the same as the one specified in the run-task instruction.
- Supported audio formats: pcm, wav, mp3, opus, speex, aac, and amr. For opus and speex formats, Ogg encapsulation is required. For the wav format, PCM encoding is required.
Receive events from the server
After you send an instruction or audio, the server sends different types of events. Each event represents a different processing stage. You must strictly follow the sequence diagram to handle these events.
There are four types of events: speech-listen, recognize-result, ai-result, and speech-end.
speech-listen event
This corresponds to process 3 in the sequence diagram. The speech-listen event is returned after the run-task instruction. It indicates that the server has received your transcription instruction and completed the initialization. You can now start sending audio.
The protocol fields are as follows:
Field | Type | Description |
|---|---|---|
header | Object | |
header.event | String | Always result-generated. |
header.task_id | String | The task_id that you specified in the run-task instruction. |
payload | Object | |
payload.output | Object | |
payload.output.action | String | Always speech-listen. |
payload.output.dataId | String | The ID of the current transcription task. You can use this ID to submit feedback. You can also use this ID to view the billing items for the task in your bill. |
recognize-result event
This corresponds to process 4 in the sequence diagram. The recognize-result event is returned after you send audio. It may also be returned after you send the finish-task instruction. This event contains the text and translation results that the server has recognized so far.
The protocol fields are as follows:
Field | Type | Description |
|---|---|---|
header | Object | |
header.event | String | Always result-generated. |
header.task_id | String | The task_id that you specified in the run-task instruction. |
payload | Object | |
payload.output | Object | |
payload.output.action | String | Always recognize-result. |
payload.output.transcription | Object | The original transcription result. |
payload.output.transcription.sentenceId | Integer | The sentence sequence number. |
payload.output.transcription.beginTime | Integer | The start time in the audio for the first character of the currently recognized part of the sentence, in ms. |
payload.output.transcription.endTime | Integer | The end time in the audio for the last character of the currently recognized part of the sentence, in ms. |
payload.output.transcription.sentenceEnd | Boolean | Indicates whether the current sentence is complete. |
payload.output.transcription.text | String | The content of the currently recognized part of the sentence. |
payload.output.transcription.words | List[Word] | Word segmentation information for the sentence. |
payload.output.translations | Object | The translation result of the transcription. |
payload.output.translations.sentenceEnd | Boolean | Indicates whether the current sentence is complete. |
payload.output.translations.translations | Object | The result set for the target translation languages. |
payload.output.translations.translations.zh | Object | Currently, only translation to Chinese is supported, so there will only be one zh object. |
payload.output.translations.translations.zh.lang | String | Set the value to zh. |
payload.output.translations.translations.zh.sentenceId | Integer | The sentence sequence number. |
payload.output.translations.translations.zh.beginTime | Integer | The start time in the audio for the first character of the currently translated part of the sentence, in ms. |
payload.output.translations.translations.zh.endTime | Integer | The end time in the audio for the last character of the currently translated part of the sentence, in ms. |
payload.output.translations.translations.zh.sentenceEnd | Boolean | Indicates whether the current sentence is complete. |
payload.output.translations.translations.zh.text | String | The content of the currently translated part of the sentence. |
payload.output.translations.translations.zh.words | List[Word] | Word segmentation information for the translated sentence. |
Field | Type | Description |
|---|---|---|
beginTime | Integer | The start time of the current word in the audio. |
endTime | Integer | The end time of the current word in the audio. |
text | String | The content of the current word. |
ai-result event
This corresponds to process 6 in the sequence diagram. The ai-result event is returned after the last recognize-result event. It represents the final transcription result, which has been corrected using the specified instruction set.
The protocol fields are as follows:
Field | Type | Description |
|---|---|---|
header | Object | |
header.event | String | Always result-generated. |
header.task_id | String | The task_id that you specified in the run-task instruction. |
payload | Object | |
payload.output | Object | |
payload.output.action | String | Always ai-result. |
payload.output.aiResult | Object | |
payload.output.aiResult.correction | String | The final result of the industrial instruction transcription. |
speech-end event
This corresponds to process 7 in the sequence diagram. The speech-end event is sent after the ai-result event. It indicates that the industrial instruction transcription is complete. You can then close the WebSocket connection.
The protocol fields are as follows:
Field | Type | Description |
|---|---|---|
header | Object | |
header.event | String | Always result-generated. |
header.task_id | String | The task_id that you specified in the run-task instruction. |
payload | Object | |
payload.output | Object | |
payload.output.action | String | This is fixed to the end of the speech. |
task-failed event
If a task fails during processing because of incorrect parameters from the client or an internal server error, the server returns a task-failed event and then closes the WebSocket connection.
The protocol fields are as follows:
Field | Type | Description |
|---|---|---|
header | Object | |
header.event | String | Always result-generated. |
header.task_id | String | The task_id that you specified in the run-task instruction. |
payload | Object | |
payload.output | Object | |
payload.output.action | String | The value is always set to task-failed. |
payload.output.errorCode | String | Error code |
payload.output.errorMessage | String | Error message |
WebSocketconnection reuse
This feature does not support connection reuse. You must create a new WebSocket connection for each task.
The connection is automatically closed if no text or binary messages are sent for 15 s.
Code examples
Error codes
Error code | Error message | Description |
|---|---|---|
InvalidParameter | Invalid parameter. For more information, see the official documentation. | The parameter is invalid. Check the parameters that you passed. |
InvalidParameter | The value of maxEndSilence is invalid. It must be between 0 and 6000. | The value of the maxEndSilence parameter is invalid. |
InvalidParameter | The term is not found. | The specified instruction set does not exist. |
InvalidParameter | The sample rate is invalid. | The value of the sample rate parameter is invalid. |
InvalidParameter | The audio format is invalid. | The value of the audio coding format parameter is invalid. |
InvalidParameter | The term is invalid. | The specified instruction set ID is invalid. |
Agent.FrameSequenceIllegal | The WebSocket frame sequence is invalid. | The instruction call sequence is invalid. |
Agent.InputActionIllegal | The input action is invalid. | The value of the action field in the instruction is invalid. |
Agent.InputAppIdIllegal | The input application ID is invalid. | The value of the application ID field is invalid. |
Agent.AppNotPublished | The application has not been published. | The specified application has not been published. |
Agent.CustomTaskIdInvalid | The custom task ID must be 16 characters long. | The length of the task ID is invalid. |
BIL.ServiceNotActivate | The user has not activated the service. | You have not activated the Tingwu Agent service. |
BIL.UserArrears | The user's account has an overdue payment. | Your account has an overdue payment. |
Agent.AppInfoNotExist | The application information does not exist. | The specified application ID information does not exist. You must first save and publish the application configuration in the console. |
ServerError | A server error occurred. | Internal server error. |