Prerequisites
- A DeepL API account with Voice API access
- Python 3.10 or later
- Headphones, if you want to hear the translation spoken
- A microphone (no microphone? see Simulate a live stream from a file)
Building with an AI coding agent?
Wire it up to the DeepL Docs MCP Server so it can search and read this documentation while it writes code. In Claude Code:Run the complete example
Install the dependencies:live_translation.py and replace YOUR_AUTH_KEY with your DeepL API key:
live_translation.py
How it works
The program does three things: it creates a session over HTTPS, streams audio to the WebSocket URL it gets back, and handles result messages until the server confirms everything is final.The session request
create_session sends a POST request with the audio format and target languages. The only required field is source_media_content_type; for raw microphone audio, that’s PCM at 16 kHz. The response contains the WebSocket URL and a one-time token, and the program connects to {streaming_url}?token={token}:
"source_language": "en" and "source_language_mode": "fixed" to the request body. This skips language detection and reduces latency. Without them, the language is detected automatically. See the Request Session reference for all parameters, including glossary and formality options.
Sending audio
send_microphone_audio sends each 200-millisecond microphone chunk as a JSON text message with the raw audio base64-encoded:
Receiving transcripts and translations
While audio is being sent, the server pushessource_transcript_update and target_transcript_update messages on the same connection:
receive_results appends concluded text to a per-language buffer and prints the buffer whenever a sentence completes, which keeps the terminal readable. A UI would also render the tentative text as a live preview that updates in place; see Understanding Voice Sessions for this delivery model.
After end_of_source_media, the server sends the remaining updates, then end_of_stream as the very last message, at which point it’s safe to close the connection. See the WebSocket Streaming reference for the full message schema.
Reconnecting after a drop
Networks drop, and the Voice API lets you resume a session instead of starting over. If the WebSocket closes unexpectedly, exchange your token for a fresh streaming URL and token, then reconnect. Session state, including configuration and translation context, is preserved.create_session().
To add this to the example, wrap the websockets.connect block in a try/except websockets.exceptions.ConnectionClosed loop that calls reconnect() and connects again with the new URL and token.
Hear the translation spoken
The Voice API can also speak the translation aloud, so listeners hear the German version while you talk. In this step you extendlive_translation.py to request translated speech and play it through your headphones.
Request translated speech
Two session fields turn on translated speech.target_media_languages names the language to speak, and the server then streams synthesized audio of each German translation alongside the text. target_media_content_type sets the audio format: raw 24 kHz PCM plays directly through sounddevice, with no decoder. Add a constant for that playback rate next to SAMPLE_RATE:
create_session:
Play the audio as it arrives
Add a player task that writes audio from a queue to your headphones. Like the microphone reader, it blocks in a worker thread so the receive loop keeps running:target_media_chunk messages, each with a data array of base64-encoded audio packets. Replace receive_results with this version, which puts every decoded packet on the queue. The finally block queues None however the loop ends, so the player finishes the remaining audio and stops instead of waiting forever:
main and run the player next to the other two tasks:
Run it with translated speech
Here’s the complete script with all the changes from this section. Save it aslive_speech_translation.py if you want to keep the text-only version, and replace YOUR_AUTH_KEY with your DeepL API key:
live_speech_translation.py
Simulate a live stream from a file
If you don’t have a microphone, or you want reproducible input while developing, stream a pre-recorded file at real-time pace instead. Set"source_media_content_type": "audio/auto" in the session request so the format is detected, and swap send_microphone_audio for a reader that paces itself:
Next steps
- See the WebSocket Streaming reference for the complete message schema and all event types.
- To understand the session flow and token lifecycle in depth, see Understanding Voice Sessions.
- To choose a voice or another audio format for translated speech, see the Request Session reference.
- To reduce bandwidth with MessagePack instead of JSON, see Message Encoding.
- For a fuller command-line version of this program, including glossary and formality options, see the DeepL Voice CLI example.
- To apply a custom glossary to your translations, see the Glossaries API.