POST /v1/audio/transcriptions

The exact contract for Flux speech to text: multipart request fields, the response for each format, receipt headers, limits and every error code.

Turns speech in an audio file into text. For a guided introduction, see Speech to text.

EndpointPOST https://api.fluxrouter.ai/v1/audio/transcriptions
Requestmultipart/form-data
AuthAuthorization: Bearer <your Flux key>
PlanPaid
StreamingNo
StatusLive

The same route also answers at /audio/transcriptions, without the /v1.

Request fields

FieldRequiredTypeNotes
fileyesfileThe audio. The format is read from the contents: wav, mp3, mp4/m4a, ogg (including Opus), webm or flac. Up to 8 MB.
modelnostringflux-voice (the default), flux-voice-accurate or flux-voice-fast. An unknown id is treated as flux-voice.
languagenostringISO-639-1 code, such as en. Leave it out to detect the language.
promptnostringNames, jargon or spellings to expect. Cut to 2,000 characters.
temperaturenonumberSampling temperature.
response_formatnostringjson (the default), verbose_json or text. srt and vtt are refused.
timestamp_granularities[]nostring, repeatableword, segment or both. Only affects verbose_json.

Sending stream=true is refused with 400: there is no streaming transcription.

Response

The body depends on response_format.

json (the default):

json
{ "text": "Let's move the launch to Thursday." }

text: the transcript as a plain text body, with no JSON around it.

verbose_json:

json
{
  "task": "transcribe",
  "language": "english",
  "duration": 3.2,
  "text": "Let's move the launch to Thursday.",
  "segments": [
    { "id": 0, "start": 0.0, "end": 3.2, "text": "Let's move the launch to Thursday." }
  ],
  "words": [
    { "word": "Let's", "start": 0.0, "end": 0.3 }
  ]
}
  • segments is always present in verbose_json. Segments can carry more fields than shown; rely on start, end and text.
  • words is present only when you send timestamp_granularities[]=word.
  • Times are in seconds from the start of the file.

Response headers

HeaderMeaning
x-flux-routed-modelThe model id that served: flux-voice, flux-voice-accurate or flux-voice-fast
x-flux-billed-secondsSeconds billed: the audio length rounded up, at least 10 seconds
x-flux-cost-usdWhat this request cost, in US dollars

Limits

LimitValue
File size8 MB
Processing time60 seconds, then 504
Requests60 requests a minute per account
Audio36,000 seconds of audio an hour per account, shared with speech

Errors

Errors use this envelope:

json
{
  "error": {
    "message": "unsupported or unrecognized audio format",
    "type": "invalid_request_error",
    "code": "unsupported_file_format",
    "param": "file"
  }
}

code and param are present only when they apply.

StatuscodeMeaningBilled
400unsupported_file_formatThe file is not audio in a format listed above.No
400none, param setA field is wrong: stream, response_format, or a missing or unreadable file. param names it.No
401noneThe key was missing or not accepted, or flux-voice is not on the key's model list.No
402premium_lockedThe key's plan does not include transcription.No
402credit_unresolvedYour credit balance could not be checked. Retry shortly.No
402another codeA spend cap or prepaid balance stopped the request. See Spend caps.No
404noneTranscription is not switched on for this deployment.No
413file_too_largeThe file is over the size limit.No
429rate_limit_errorOver the per-account request rate or hourly audio budget. Wait, then retry.No
502capability_unavailableTranscription failed upstream. Retry.No
504capability_unavailableTranscription took too long. Retry, or send a shorter file.No

Fixes for each are on Speech to text problems.

Example requests

bash
curl https://api.fluxrouter.ai/v1/audio/transcriptions \
  -H "Authorization: Bearer sk-YOUR-FLUX-KEY" \
  -F "file=@meeting.m4a" \
  -F "model=flux-voice"

Word timestamps, with the receipt headers printed:

bash
curl -i https://api.fluxrouter.ai/v1/audio/transcriptions \
  -H "Authorization: Bearer $FLUX_API_KEY" \
  -F "file=@note.ogg" \
  -F "model=flux-voice" \
  -F "language=en" \
  -F "response_format=verbose_json" \
  -F "timestamp_granularities[]=word"

With Python's requests, reading the cost:

python
import requests

with open("meeting.m4a", "rb") as audio:
    r = requests.post(
        "https://api.fluxrouter.ai/v1/audio/transcriptions",
        headers={"Authorization": "Bearer sk-YOUR-FLUX-KEY"},
        files={"file": ("meeting.m4a", audio)},
        data={"model": "flux-voice", "response_format": "json"},
        timeout=90,
    )

r.raise_for_status()
print(r.json()["text"])
print(r.headers["x-flux-billed-seconds"], r.headers["x-flux-cost-usd"])