> ## Documentation Index
> Fetch the complete documentation index at: https://docs.camb.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Dubbing

> Dub a video into another language using the Python or TypeScript SDK

## Overview

Translate the audio of any video into another language while preserving the original speaker's voice characteristics. Dubbing is useful for content localization, accessibility, and reaching global audiences without re-recording.

The dubbing pipeline is asynchronous: you submit a job, poll until it completes, then retrieve the dubbed output.

### Prerequisites

<Steps>
  <Step title="Create an account">
    Sign up at [CAMB.AI Studio](https://studio.camb.ai) if you haven't already.
  </Step>

  <Step title="Get your API key">
    Go to **Settings → API Keys** in Studio and copy your key. See [Authentication](/getting-started/authentication) for details.
  </Step>

  <Step title="Install the SDK">
    <CodeGroup>
      ```bash Python theme={null}
      pip install camb-sdk
      ```

      ```bash TypeScript theme={null}
      npm install @camb-ai/sdk
      ```
    </CodeGroup>

    Skip this step if you're using the [direct API](/tutorials/direct-api).
  </Step>

  <Step title="Set your API key to use in your code">
    ```bash theme={null}
    export CAMB_API_KEY="your_api_key_here"
    ```
  </Step>
</Steps>

***

## Code

<CodeGroup>
  ```python Python theme={null}
  import os
  import time
  from camb.client import CambAI
  from camb.types.language_enums import Languages

  client = CambAI(api_key=os.getenv("CAMB_API_KEY"))

  response = client.dub.create_dub(
      video_url="your_accessible_video_url",
      source_language=Languages.EN_US,  # English (or check client.languages.get_source_languages())
      target_languages=[Languages.HI_IN],  # list of Languages, e.g. [Languages.HI_IN, Languages.FR_FR]
      transcription_mode="fast",
  )
  task_id = response.task_id
  print(f"Dub Task created with ID: {task_id}")

  while True:
      status_response = client.dub.get_dubbing_status(task_id=task_id)
      print(f"Current Status: {status_response.status}")
      if status_response.status == "SUCCESS":
          dubbed_run_info = client.dub.get_dubbed_run_info(status_response.run_id)
          print(f"Audio URL: {dubbed_run_info.audio_url}")
          print(f"Transcript: {dubbed_run_info.transcript}")
          print(f"Video URL: {dubbed_run_info.video_url}")
          break
      time.sleep(5)
  ```

  ```javascript TypeScript theme={null}
  import { CambClient, CambApi } from '@camb-ai/sdk';

  const client = new CambClient({
      apiKey: process.env.CAMB_API_KEY
  });

  async function dubVideo() {
      // Step 1: Submit the dubbing job
      const response = await client.dub.endToEndDubbing({
          video_url: 'your_accessible_video_url',
          source_language: CambApi.Languages.EN_US,
          target_languages: [CambApi.Languages.HI_IN], // pass an array, e.g. [HI_IN, FR_FR]
          transcription_mode: 'fast'
      });

      const taskId = response.task_id;
      console.log(`Dub Task created with ID: ${taskId}`);

      // Step 2: Poll until complete
      while (true) {
          const statusResponse = await client.dub.getEndToEndDubbingStatus({
              task_id: taskId
          });
          console.log(`Current Status: ${statusResponse.status}`);

          if (statusResponse.status === 'SUCCESS') {
              const dubbedRunInfo = await client.dub.getDubbedRunInfo({
                  run_id: statusResponse.run_id
              });
              console.log(`Audio URL: ${dubbedRunInfo.audio_url}`);
              console.log(`Transcript: ${dubbedRunInfo.transcript}`);
              console.log(`Video URL: ${dubbedRunInfo.video_url}`);
              break;
          }

          await new Promise(resolve => setTimeout(resolve, 5000));
      }
  }

  dubVideo();
  ```
</CodeGroup>

***

## Parameters

### Required

| Parameter          | Type             | Description                                                                                                                                                |
| ------------------ | ---------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `video_url`        | string           | Publicly accessible URL of the source video (YouTube links and direct URLs are supported)                                                                  |
| `source_language`  | `Languages` enum | Language spoken in the source video                                                                                                                        |
| `target_languages` | `Languages[]`    | List of languages to dub into. Pass a single-element list (`[Languages.HI_IN]`) for one target, or multiple to dub into several languages in a single job. |

### Optional

| Parameter                      | Type             | Description                                                                                                                                                        |
| ------------------------------ | ---------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `target_language`              | `Languages` enum | Single-language convenience alternative to `target_languages`. Prefer `target_languages=[Languages.HI_IN]` — `target_language` exists for backwards compatibility. |
| `project_name`                 | string           | Label for the job in your dashboard                                                                                                                                |
| `project_description`          | string           | Additional notes for the job                                                                                                                                       |
| `selected_audio_tracks`        | integer\[]       | Specific audio track indices from the source video                                                                                                                 |
| `add_output_as_an_audio_track` | boolean          | Attach the dubbed audio as an extra track instead of replacing the original                                                                                        |

### Language Enum

Use the `Languages` enum (Python) or `CambApi.Languages` (TypeScript) to specify languages:

<CodeGroup>
  ```python Python theme={null}
  from camb.types.language_enums import Languages

  # Examples
  Languages.EN_US   # English (US)
  Languages.ES_ES   # Spanish (Spain)
  Languages.FR_FR   # French
  Languages.DE_DE   # German
  Languages.HI_IN   # Hindi
  Languages.JA_JP   # Japanese
  Languages.ZH_CN   # Chinese (Simplified)
  ```

  ```javascript TypeScript theme={null}
  import { CambApi } from '@camb-ai/sdk';

  // Examples
  CambApi.Languages.EN_US   // English (US)
  CambApi.Languages.ES_ES   // Spanish (Spain)
  CambApi.Languages.FR_FR   // French
  CambApi.Languages.DE_DE   // German
  CambApi.Languages.HI_IN   // Hindi
  CambApi.Languages.JA_JP   // Japanese
  CambApi.Languages.ZH_CN   // Chinese (Simplified)
  ```
</CodeGroup>

***

## Tips

* **Video URL:** The URL must be publicly accessible. YouTube video links and direct file URLs (MP4, WebM) are both supported.
* **Polling timeout:** For long videos, cap your polling loop (e.g. 60 attempts × 5s = 5 minutes) and handle the timeout gracefully.
* **Multiple targets:** `target_languages` accepts an array — pass several languages to dub into all of them in a single job, which is more efficient than submitting separate jobs.
* **Transcripts:** The result object includes a `transcript` field with per-segment timing data, useful for subtitle generation.

***

## Next Steps

<CardGroup cols={2}>
  <Card title="End-to-End Dubbing API" icon="book" href="/api-reference/endpoint/end-to-end-dubbing">
    Full API reference for the dubbing endpoint.
  </Card>

  <Card title="Get Dubbing Status" icon="clock" href="/api-reference/endpoint/get-end-to-end-dubbing-status">
    Status polling endpoint reference.
  </Card>

  <Card title="Get Dubbed Run Info" icon="film" href="/api-reference/endpoint/get-dubbed-run-info">
    Retrieve the dubbed output URLs and transcript.
  </Card>

  <Card title="Voice Cloning" icon="mic" href="/tutorials/voice-cloning">
    Clone a custom voice for use in speech generation.
  </Card>
</CardGroup>
