Transcribe audio to text. Accepts multipart/form-data and returns an OpenAI Whisper-compatible response. Supports up to 23 Indic languages, with optional translation and transliteration modes depending on the model.
STT model ID. Call GET /v1/models and pick an STT model.
language_code
string
Language hint in BCP-47 format (e.g. "hi-IN", "en-IN"). Omit to let the model auto-detect.
STT models
Call GET /v1/models for the STT models available to your account and the languages each one supports. Models differ in language coverage and which output modes they offer. Each STT entry also carries a streaming boolean — check it before opening a WebSocket, since not every STT model supports realtime:
AdvancedUp to 23 languages, with multiple output modes (transcribe, translate, verbatim, translit, codemix) and word/segment timestamps.
StandardCommon-language transcription in the original language — simpler and faster for everyday use.
Output modes
The mode controls what the model returns for each audio input. Support is a property of the model — GET /v1/models indicates which modes a model offers:
transcribeDefault. Returns the transcript in the original spoken language with proper formatting.
translateTranslates Indic language speech directly to English text.
verbatimWord-for-word transcription without normalization or punctuation correction.
translitRomanizes the transcript — output is in Latin script.
codemixMixed script output — blends English and native scripts for code-switched speech.
# Translate Indic speech directly to English.
# Translation is a property of the model — pick one that offers it
# (see the Output modes section and GET /v1/models).
curl https://api.inferexai.in/v1/audio/transcriptions \
-H "Authorization: Bearer sk-live-your-key" \
-F "file=@audio.wav" \
-F "model=inferex-stt"
Python
transcribe.py
from inferexai import InferexAI
client = InferexAI(api_key="sk-live-your-key")
with open("audio.wav", "rb") as f:
transcript = client.audio.transcriptions.create(
model="inferex-stt", # use an STT model ID from /v1/models
file=f,
language="hi-IN",
)
print(transcript.text)
Node.js
transcribe.ts
import InferexAI from "inferexai";
import fs from "fs";
const client = new InferexAI({ apiKey: "sk-live-your-key" });
const transcript = await client.audio.transcriptions.create({
model: "inferex-stt",
file: fs.createReadStream("audio.wav"),
language: "hi-IN",
});
console.log(transcript.text);
Response
Returns a JSON object. text always contains the full transcript. Optional fields appear when returned by the model.
With word/segment timestamps (when supported by the model):
response-with-segments.json
{
"text": "Hello, how can I help you today?",
"language": "en",
"duration": 3.42,
"segments": [
{ "id": 0, "start": 0.0, "end": 1.8, "text": "Hello, how can I help" },
{ "id": 1, "start": 1.8, "end": 3.42, "text": " you today?" }
]
}
Long recordings & diarization (async jobs)
The synchronous endpoint above is for short clips (up to ~30 seconds). For a long recording — a call, a meeting — and for speaker diarization (labeling who spoke when across the whole file), use an asynchronous transcription job: submit the audio once, receive a job id, then poll that id until the transcript is ready. Diarization is only consistent when the whole file is processed together, so it is exposed here rather than on the synchronous endpoint.
POST/v1/audio/transcriptions/jobs
Parameter
Type
Description
filerequired
file
The recording to transcribe.
modelrequired
string
An STT model that supports async jobs (see GET /v1/models).
diarize
boolean
Label speakers across the file. Defaults to true.
num_speakers
integer
Hint for the expected number of speakers, when known.
language_code
string
BCP-47 language hint (e.g. "hi-IN"). Omit to auto-detect.
1. Create the job
bash
# Long recordings (over ~30s) with speaker diarization run as an
# asynchronous job: submit once, then poll the job id until it is done.
curl https://api.inferexai.in/v1/audio/transcriptions/jobs \
-H "Authorization: Bearer sk-live-your-key" \
-F "file=@call-recording.wav" \
-F "model=inferex-stt" \
-F "diarize=true"
# => { "id": "txjob_...", "status": "queued" }
2. Poll until complete
Poll GET /v1/audio/transcriptions/jobs/{id} every few seconds. While it runs, status is queued or processing; when done it is completed (or failed).
segments carries the diarized transcript. Each segment has a speaker label (SPEAKER_00, SPEAKER_01, …) that is consistent for the whole recording — mapping a label to a real role (e.g. agent vs. customer) is up to your application.
job.json
{
"id": "txjob_xxx",
"object": "transcription.job",
"status": "completed",
"language": "en-IN",
"duration": 1834.2,
"text": "full transcript of the whole recording ...",
"segments": [
{ "speaker": "SPEAKER_00", "start": 0.0, "end": 4.2, "text": "Thank you for calling, how may I help?" },
{ "speaker": "SPEAKER_01", "start": 4.5, "end": 9.1, "text": "Hi, I have a question about my bill." }
]
}
List your recent jobs with GET /v1/audio/transcriptions/jobs. Billing is by audio duration on completion; a failed job is not charged.
Realtime transcription (WebSocket)
For live audio — transcribing a call as it happens — open a WebSocket, stream PCM audio up, and receive transcript events back with sub-second latency. The event shape follows the OpenAI Realtime transcription API, so a client written against it works unchanged. Realtime does not label speakers; for speaker diarization use the async jobs endpoint above.
WS/v1/audio/transcriptions/stream
Query param
Type
Description
modelrequired
string
An STT model that supports realtime streaming (see GET /v1/models).
language
string
BCP-47 language hint (e.g. "hi-IN"). Omit to auto-detect.
sample_rate
integer
Audio sample rate. Defaults to 16000; 8000 also supported.
encoding
string
pcm_s16le (default), mulaw, alaw, or linear32. Must match your audio.
return_timestamps
boolean
Include start/end times on completed segments. Defaults to true.
1. Connect
bash
# Realtime transcription over a WebSocket. Connect, stream PCM audio up,
# receive OpenAI Realtime-compatible transcript events back.
wss://api.inferexai.in/v1/audio/transcriptions/stream?model=inferex-stt-realtime&language=en-IN&sample_rate=16000&encoding=pcm_s16le
# Auth on the handshake header (server clients):
# Authorization: Bearer sk-live-your-key
# or, for browsers that can't set WS headers, add ?api_key=sk-live-your-key
2. Stream audio up
Send audio either as base64 in an input_audio_buffer.append message, or as raw binary WebSocket frames. With server-side voice activity detection, utterances are committed automatically.
JSON
// client -> gateway (text frames), OpenAI Realtime shape:
{ "type": "input_audio_buffer.append", "audio": "<base64 PCM16>" }
{ "type": "input_audio_buffer.commit" } // flush; server-VAD auto-commits
// ...or just send the raw PCM bytes as a binary WS frame (no base64) —
// convenient for a telephony pipe. Both forms are accepted.
3. Receive transcript events
...transcription.delta events carry incremental text as it is recognized; ...transcription.completed carries the final, authoritative transcript for each utterance. Billing is by audio duration when the connection closes.
JSON
// gateway -> client (text frames). request_id is on the 101 upgrade
// response headers too, so you can correlate a connection end-to-end
// even if you only log the WS frames:
{ "type": "transcription_session.created",
"session": { "model": "...", "sample_rate": 16000 }, "request_id": "req_abc123" }
{ "type": "input_audio_buffer.speech_started" }
{ "type": "conversation.item.input_audio_transcription.delta", "delta": "hello wor" }
{ "type": "conversation.item.input_audio_transcription.completed",
"transcript": "hello world", "start": 0.5, "end": 2.3 }
{ "type": "input_audio_buffer.speech_stopped" }
{ "type": "transcription_session.done" }
// on failure, the same request_id is on the error frame — quote it when
// contacting support:
{ "type": "error", "error": { "message": "...", "code": "...", "request_id": "req_abc123" } }
Supported languages
Pass the language code in BCP-47 format. Omit for auto-detection. Coverage varies by model (up to 23 languages); see GET /v1/models for what your selected model supports.
Hindihi-IN
English (India)en-IN
Tamilta-IN
Telugute-IN
Kannadakn-IN
Malayalamml-IN
Marathimr-IN
Gujaratigu-IN
Bengalibn-IN
Punjabipa-IN
Odiaor-IN
Assameseas-IN
Error codes
Errors from the sync, async-job, and realtime endpoints share the same {"error": {"message", "type", "code"}} envelope — on the WebSocket it arrives as an {"type": "error", "error": {...}} frame instead of an HTTP response.
401
invalid_api_key
Missing or invalid API key.
402
insufficient_credit
Wallet is empty. Top up credits before retrying.
403
kyc_required
KYC verification is required before this call.
404
model_not_found
The model ID does not exist or is not available to your account.
413
(plain, not JSON)
Audio file exceeds the 25 MB upload limit — rejected by the edge proxy before reaching the API, so the body is a plain error page, not the JSON envelope.