Skip to main content
Closed alpha. This API may change without notice and is only available to select DeepL customers. See alpha and beta features for details. To request access, contact your customer success manager.
The Voice Translate Job API translates pre-recorded audio files asynchronously. You submit a file, poll until each target is ready, then download the results. One source file can produce multiple outputs in one job: plain text transcripts, SRT subtitles, and translated speech audio in any combination. This guide walks through all four steps with a concrete example: an English MP3 podcast episode translated into German text and Spanish audio.

Overview

  • The API separates job creation from file upload and uses pre-signed URLs for direct object storage access
  • Job targets are tracked independently, each transitioning through its own status values
  • Per-target results must be checked individually; partial failures do not affect other targets in the same job

Prerequisites

  • A DeepL API key with Voice Translate Job access
  • An audio file to translate (see supported source formats and limits)
  • curl for the HTTP requests; wget or any HTTP client for the download

Create a job

Send a POST request to /v1/jobs/voice/translate with the source file metadata and a list of targets. The API returns an upload URL for your audio file; it does not accept the file directly.
content_length must be the exact byte size of the file. The API uses this to pre-allocate the upload URL and rejects uploads that don’t match. The response contains the job ID and a pre-signed upload URL:
Save the job_id and upload_url. You have 5 minutes to complete the upload before the URL expires.
API Free users should use https://api-free.deepl.com instead of https://api.deepl.com.

Upload the source file

PUT your audio file directly to the upload_url from the previous step. This is a direct upload to object storage, not to the DeepL API, so no authorization header is needed.
The Content-Type header must match the content_type you declared when creating the job. A successful upload returns HTTP 200 with an empty body. Processing starts automatically once the upload is complete.
You must upload within 5 minutes of creating the job. If the upload URL expires, create a new job.

Poll for status

Check the job status by sending a GET request to /v1/jobs/voice/translate/{job_id}. Results for each target are returned in the same order as the targets in your create request.
While processing is still underway, targets will be in processing status:
Poll every 10-30 seconds until each target reaches complete or failed. See the status lifecycle reference for the full set of intermediate statuses. When a target reaches complete, its result object includes a download_url:
Targets can fail independently. A failed target does not affect other targets in the same job. Check each result’s status field before attempting to download.

Download results

Fetch each completed result from its download_url. Like the upload, this is a direct request to object storage, so no authorization header is needed (access is controlled by the pre-signed URL itself).
For audio targets, save the file with an extension matching the format you requested (.pcm, .mp3, .wav, etc.).
Download results within 1 hour of the upload completing. After that window, results expire and the job returns 404. Once all results are downloaded, assets are also marked for deletion.

Full example script

This Python script runs all four steps end to end. Replace the placeholder values with your own.
This is a minimal example. It reads the full audio file into memory, which is not suitable for large files. Production code should open the file in streaming mode rather than loading it all at once.
translate_audio.py

Next steps