Skip to content

Translation

The problem. A support agent in Paris, a customer speaking Spanish; a conference streamed to an international audience. Translation turns each sentence into the languages you choose while the person is still speaking: live subtitles, a bilingual call log, a meeting record in your team’s language.

Where it works. solaria-3 only. The translation is made from the audio of each utterance, not from its transcript.

{
"model": "solaria-3",
"realtime_processing": {
"translation": true,
"translation_config": { "target_languages": ["en", "fr"] }
}
}

Each program streams a 16-bit WAV file and prints what comes back. Put your API key in the GLADIA_API_KEY environment variable, then run python translation.py meeting.wav.

translation.py
# pip install gladiaio-sdk
import os
import sys
import threading
import wave
from gladiaio_sdk import GladiaClient, LiveV2InitRequest
API_URL = os.environ.get("GLADIA_API_URL", "https://eu1.api.gladia.io")
API_KEY = os.environ["GLADIA_API_KEY"]
with wave.open(sys.argv[1]) as wav: # a 16-bit PCM WAV file
rate, channels = wav.getframerate(), wav.getnchannels()
audio = wav.readframes(wav.getnframes())
config = {
"encoding": "wav/pcm",
"sample_rate": rate,
"bit_depth": 16,
"channels": channels,
"model": "solaria-3",
"language_config": {
"languages": [
"es"
]
},
"realtime_processing": {
"translation": True,
"translation_config": {
"target_languages": [
"en",
"fr"
]
}
}
}
client = GladiaClient(api_key=API_KEY, api_url=API_URL)
session = client.live_v2().start_session(LiveV2InitRequest.from_dict(config))
ended, errors = threading.Event(), []
@session.on("message")
def on_message(message):
if message.type == "transcript" and message.data.is_final:
print(message.data.utterance.text)
elif message.type == "translation" and message.data.translated_utterance:
translated = message.data.translated_utterance
print(f" {translated.language}: {translated.text}")
session.on("error", errors.append)
session.once("ended", lambda _: ended.set())
step = rate * channels * 2 // 10 # 100 ms of audio per chunk
for start in range(0, len(audio), step):
session.send_audio(audio[start : start + step]) # live audio: send each chunk as it is captured
session.stop_recording()
ended.wait(timeout=60)
sys.exit(1 if errors or not ended.is_set() else 0)

Each final transcript is followed by one translation message per target language:

{
"type": "translation",
"session_id": "0199d7a2-5c3e-7b41-9f0a-3c2d1e4f5a6b",
"error": null,
"data": {
"utterance_id": "00_00000003",
"utterance": { "text": "¿Dónde está la estación?", "start": 12.4, "end": 13.9, "language": "es", "channel": 0 },
"original_language": "es",
"target_language": "en",
"translated_utterance": { "text": "Where is the station?", "start": 12.4, "end": 13.9, "language": "en", "channel": 0, "confidence": 1, "words": [] }
}
}

The session’s result (GET /v2/live/{id}, post_final_transcript) has a translation block: one result per target language, with its utterances and full text.

  • solaria-3 only. With another model, no model can serve the session: POST /v2/live answers 500 “no inference endpoint available”.
  • Only the languages below. Another code passes the creation, then the session is refused when it starts: the WebSocket closes with code 1011 and the reason rejected: translation: target language(s) [...] not served.
  • Not with PII redaction. The translation is made from the audio and would carry the redacted data back: a session with both pii and translation is refused when it starts (1011, rejected: ...).
  • Finals only. Partials are not translated. Translations arrive shortly after their final, never before it, and never delay it.
  • Same language, same text. An utterance already in a target language comes back as transcribed.
  • Long utterances. Translation reads up to 60 seconds of an utterance: set maximum_duration_without_endpointing (at most 60) for monologues without pauses.
  • A translation can fail alone. It then comes with error set and translated_utterance: null; the transcript is not affected. Show the original text as a fallback.
  • At the end, the session waits up to 5 seconds for the last translations before end_session.
  • Spelling and vocabulary do not apply to translations (they come from the audio).
  • Accepted, not applied. Gladia’s cloud fields model, context, context_adaptation, informal, lipsync and match_original_utterances in translation_config are accepted for compatibility and have no effect.
Target languageCode
Afrikaansaf
Amharicam
Arabicar
Assameseas
Belarusianbe
Bulgarianbg
Banglabn
Catalanca
Danishda
Germande
Englishen
Spanishes
Persianfa
Frenchfr
Galiciangl
Indonesianid
Italianit
Japaneseja
Khmerkm
Koreanko
Lingalaln
Laolo
Malayms
Burmesemy
Nepaline
Dutchnl
Norwegianno
Pashtops
Portuguesept
Romanianro
Russianru
Somaliso
Swedishsv
Thaith
Vietnamesevi
Wolofwo
Yorubayo
Chinesezh
symptom cause fix
500 “no inference endpoint available” at creation the model is not solaria-3 set "model": "solaria-3"
WebSocket closed 1011 “rejected: translation: target language(s)…” a target not in the list use the codes above
WebSocket closed 1011 “rejected: … pii redaction” pii and translation together drop one of them
no translation message messages_config.receive_realtime_processing_events: false turn it back on, or read the session’s result