Loli 2.0
Realtime STT (Manual)
Start with mode manual. The server does not emit partials or detect silence. It buffers PCM after the previous commit and returns exactly one final segment when the client sends commit. A commit needs at least 0.2 seconds of audio; an empty or short commit produces a recoverable bad_request error, and a short buffer remains for more PCM. stop commits a sufficiently long trailing buffer, discards a shorter fragment, then sends final and closed.
WS
/api/public/v1/stt/ws?token=<stt_key>On this page
Code examples
const ws = new WebSocket(
"wss://studio.evomlabs.com/api/public/v1/stt/ws" +
"?token=stt_sk_live_YOUR_KEY&language=auto"
);
ws.addEventListener("open", () => {
ws.send(JSON.stringify({
type: "start",
mode: "auto",
language: "auto",
sample_rate: 48000,
format: "pcm_s16le",
}));
});
ws.addEventListener("message", (event) => {
const message = JSON.parse(event.data);
if (message.type === "partial" || message.type === "segment") {
renderTranscript(message.combined_text);
}
if (message.type === "final") {
renderTranscript(message.text);
}
if (message.type === "error") {
console.error(message.code, message.message);
}
});
// Send PCM16 frames with ws.send(arrayBuffer).
function stopTranscription() {
if (ws.readyState === WebSocket.OPEN) {
ws.send(JSON.stringify({ type: "stop" }));
}
}
// Start with: { "type": "start", "mode": "manual", ... }
// Send PCM16 frames, then commit exactly that buffered speech:
ws.send(JSON.stringify({ type: "commit" }));
// The server returns one final segment. Send commit again for the next turn,
// or stop to commit a sufficiently long trailing buffer and close the session.
ws.send(JSON.stringify({ type: "stop" }));Request
| Field | Type | Required | Default | Description |
|---|---|---|---|---|
type | "start" | Yes | - | Use start. |
mode | "auto" | "manual" | No | manual | auto uses server VAD; manual waits for a client commit. |
language | string | No | auto | One of the language modes listed above. |
sample_rate | integer | No | 16000 | Integer binary-input rate from 8,000 to 192,000 Hz. |
format | "pcm_s16le" | No | pcm_s16le | Exactly pcm_s16le: mono signed 16-bit little-endian PCM. |
session_id | string | No | Server generated | Optional client-provided identifier. |
Send stop before closing
Send a stop message to end the session. The server then emits final, followed by closed. Closing the socket without sending stop cancels the session and does not guarantee a final transcript.
Response
Events
// Server to client
{ "type": "started", "session_id": "session_id", "mode": "auto", "language": "auto",
"sample_rate": 16000, "provider": "loli-asr", "model": "Loli 2.0" }
{ "type": "partial", "index": 0, "text": "live window text",
"committed_text": "", "live_text": "live utterance text",
"combined_text": "live utterance text", "is_final": false,
"language": "vi", "latency_ms": 210 }
{ "type": "segment", "index": 0, "text": "committed utterance",
"committed_text": "committed utterance", "live_text": "",
"combined_text": "committed utterance", "is_final": true,
"language": "vi", "latency_ms": 350 }
{ "type": "final", "text": "Toàn bộ transcript", "language": "vi",
"is_final": true, "provider": "loli-asr", "model": "Loli 2.0",
"latency_ms": 4100 }
{ "type": "closed", "session_id": "session_id", "reason": "stopped" }
{ "type": "error", "session_id": "session_id-or-null",
"message": "Error description", "code": "bad_request" }Note
A partial can be replaced by a newer partial for the same utterance; a segment commits one utterance at a silence boundary. Use combined_text to display the transcript so far.
Errors
REST failures use the documented error envelope. Handle the error code instead of matching the human-readable message.
Error codesWas this page helpful?