VOICE / use-stt-language-and-format

Voice

Format speech-to-text with language and Inverse Text Normalization

Format speech-to-text with language and Inverse Text Normalization

Set language so spoken numbers, currencies, and units convert to written form. On batch REST you also need format=true (requires language). On streaming WebSocket, setting language alone enables Inverse Text Normalization. Base flows: Transcribe audio with the Voice API and Stream speech to text over WebSocket.

Batch REST

POST https://api.x.ai/v1/stt. Put option fields before file.

curl -X POST https://api.x.ai/v1/stt \
  -H "Authorization: Bearer $XAI_API_KEY" \
  -F format=true \
  -F language=en \
  -F file=@/path/to/meeting.mp3

Example output shape when ITN runs:

{
  "text": "The balance is $167,983.15.",
  "language": "en",
  "duration": 3.45
}

format=true without language returns 400.

Streaming WebSocket

Add language as a query param on wss://api.x.ai/v1/stt. There is no separate format query param on the stream.

wss://api.x.ai/v1/stt?sample_rate=16000&encoding=pcm&interim_results=true&language=en

Proxy the WebSocket through your backend so the API key stays off the client.

Language codes for formatting

The STT guide lists formatting codes such as en, es, fr, de, ja, ko, pt, ar, cs, da, nl, fil, hi, id, it, mk, ms, fa, pl, ro, ru, sv, th, tr, and vi. The model still transcribes those languages when language is unset; setting the code turns on written-form formatting for numbers, currencies, and units.

Pitfalls

  • Batch: format=true requires language. Stream: language alone is enough for ITN.
  • Put multipart options before file so streamable uploads do not drop late fields.
  • Console API credits are separate from SuperGrok's weekly pool on grok.com.
  • Never put the API key in client-side WebSocket code; proxy through your backend.