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

# Генерация видео: Seedance 2.0

> Seedance 2.0: текст / изображение / первый-последний кадр / референс-видео → видео со встроенным звуком. OpenAI-совместимый асинхронный API, примеры на curl и Python

Seedance 2.0 (ByteDance) — мультимодальная модель генерации видео. Поддерживает четыре типа входных данных: **текст-в-видео, изображение-в-видео, первый-последний кадр и референс-видео**, а **сгенерированное видео по умолчанию содержит синхронный звук**. RuAPI предоставляет **OpenAI-совместимый асинхронный API**: отправить задачу → опрашивать статус → скачать видео. Оплата в USDT, без зарубежной карты.

<Tip>
  **Звук включён по умолчанию** — видео Seedance 2.0 содержит синхронную аудиодорожку (реплики / фоновый звук / эффекты), никаких дополнительных параметров не нужно.
</Tip>

<Warning>
  **Готовое видео хранится только 7 дней.** Скачайте и сохраните его сразу после генерации — по истечении срока ссылка перестанет работать.
</Warning>

## Доступные модели

| ID модели                  | Описание                                |
| -------------------------- | --------------------------------------- |
| `doubao-seedance-2.0-fast` | Быстрее и дешевле, вариант по умолчанию |
| `doubao-seedance-2.0`      | Полная версия с более высоким качеством |

Актуальные цены — на **[странице цен](https://www.ruapi.ai/pricing)** (видео тарифицируется по токенам).

## Адрес API и авторизация

* **Base URL**: `https://www.ruapi.ai/v1`
* **Авторизация**: заголовок `Authorization: Bearer sk-ВАШ_КЛЮЧ` (создаётся в панели, раздел «Токены»)

Генерация **асинхронная**, всего три шага:

<Steps>
  <Step title="Отправить задачу">
    `POST /v1/videos` → возвращает `id` задачи
  </Step>

  <Step title="Опрашивать статус">
    `GET /v1/videos/{id}` → пока `status` не станет `completed`
  </Step>

  <Step title="Скачать видео">
    `GET /v1/videos/{id}/content` → получить MP4
  </Step>
</Steps>

## Шаг 1. Отправить задачу (текст-в-видео)

<CodeGroup>
  ```bash curl theme={null}
  curl https://www.ruapi.ai/v1/videos \
    -H "Authorization: Bearer sk-ВАШ_КЛЮЧ" \
    -H "Content-Type: application/json" \
    -d '{
      "model": "doubao-seedance-2.0-fast",
      "prompt": "Ночной город, неон отражается на мокром асфальте, киберпанк, камера медленно наезжает",
      "seconds": "5",
      "metadata": { "resolution": "720p", "ratio": "16:9" }
    }'
  ```

  ```python Python (requests) theme={null}
  import requests

  resp = requests.post(
      "https://www.ruapi.ai/v1/videos",
      headers={"Authorization": "Bearer sk-ВАШ_КЛЮЧ"},
      json={
          "model": "doubao-seedance-2.0-fast",
          "prompt": "Ночной город, неон отражается на мокром асфальте, киберпанк, камера медленно наезжает",
          "seconds": "5",
          "metadata": {"resolution": "720p", "ratio": "16:9"},
      },
  )
  task_id = resp.json()["id"]
  print("Задача отправлена:", task_id)
  ```

  ```javascript Node.js (fetch) theme={null}
  const resp = await fetch("https://www.ruapi.ai/v1/videos", {
    method: "POST",
    headers: {
      Authorization: "Bearer sk-ВАШ_КЛЮЧ",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      model: "doubao-seedance-2.0-fast",
      prompt: "Ночной город, неон отражается на мокром асфальте, киберпанк, камера медленно наезжает",
      seconds: "5",
      metadata: { resolution: "720p", ratio: "16:9" },
    }),
  });
  const { id } = await resp.json();
  console.log("Задача отправлена:", id);
  ```
</CodeGroup>

Ответ (`id` — это номер задачи, он нужен для следующих двух шагов):

```json theme={null}
{
  "id": "task_guXmm9BZpLpYaxfky7mkR2kSlRtgDSe9",
  "object": "video",
  "model": "doubao-seedance-2.0-fast",
  "status": "queued",
  "progress": 0,
  "created_at": 1783579686
}
```

## Шаг 2. Опрашивать статус

Запрашивайте по маршруту `GET /v1/videos/{id}` примерно раз в 5 секунд. `status` проходит путь `queued → in_progress → completed`.

<CodeGroup>
  ```bash curl theme={null}
  curl https://www.ruapi.ai/v1/videos/task_ВАШ_ID_ЗАДАЧИ \
    -H "Authorization: Bearer sk-ВАШ_КЛЮЧ"
  ```

  ```python Python (requests) theme={null}
  import requests

  r = requests.get(
      f"https://www.ruapi.ai/v1/videos/{task_id}",
      headers={"Authorization": "Bearer sk-ВАШ_КЛЮЧ"},
  ).json()
  print(r["status"], r.get("progress"))
  ```
</CodeGroup>

После завершения (`metadata.url` — ссылка для скачивания):

```json theme={null}
{
  "id": "task_guXmm9BZpLpYaxfky7mkR2kSlRtgDSe9",
  "object": "video",
  "status": "completed",
  "progress": 100,
  "metadata": {
    "url": "https://www.ruapi.ai/v1/videos/task_guXmm9BZpLpYaxfky7mkR2kSlRtgDSe9/content"
  }
}
```

## Шаг 3. Скачать видео

<CodeGroup>
  ```bash curl theme={null}
  curl -L https://www.ruapi.ai/v1/videos/task_ВАШ_ID_ЗАДАЧИ/content \
    -H "Authorization: Bearer sk-ВАШ_КЛЮЧ" \
    -o seedance.mp4
  ```

  ```python Python (requests) theme={null}
  video = requests.get(
      f"https://www.ruapi.ai/v1/videos/{task_id}/content",
      headers={"Authorization": "Bearer sk-ВАШ_КЛЮЧ"},
  )
  with open("seedance.mp4", "wb") as f:
      f.write(video.content)
  print("Сохранено: seedance.mp4")
  ```
</CodeGroup>

## Полный пример: весь процесс одним скриптом

Скопируйте и запустите, подставив свой `sk-ВАШ_КЛЮЧ`:

```python Python theme={null}
import time
import requests

BASE = "https://www.ruapi.ai/v1"
HEADERS = {"Authorization": "Bearer sk-ВАШ_КЛЮЧ"}

# 1) Отправить задачу
resp = requests.post(
    f"{BASE}/videos",
    headers=HEADERS,
    json={
        "model": "doubao-seedance-2.0-fast",
        "prompt": "Ночной город, неон отражается на мокром асфальте, киберпанк, камера медленно наезжает",
        "seconds": "5",
        "metadata": {"resolution": "720p", "ratio": "16:9"},
    },
)
resp.raise_for_status()
task_id = resp.json()["id"]
print("Задача отправлена:", task_id)

# 2) Опрашивать до завершения (обычно 1–3 минуты)
while True:
    r = requests.get(f"{BASE}/videos/{task_id}", headers=HEADERS).json()
    print("Статус:", r.get("status"), r.get("progress"))
    if r.get("status") == "completed":
        break
    if r.get("status") == "failed":
        raise RuntimeError(f"Ошибка генерации: {r.get('error')}")
    time.sleep(5)

# 3) Скачать (результат хранится 7 дней — сохраните сразу)
video = requests.get(f"{BASE}/videos/{task_id}/content", headers=HEADERS)
with open("seedance.mp4", "wb") as f:
    f.write(video.content)
print("Сохранено: seedance.mp4")
```

## Параметры

Поля верхнего уровня:

| Поле       | Тип    | Описание                                                                     |
| ---------- | ------ | ---------------------------------------------------------------------------- |
| `model`    | string | `doubao-seedance-2.0-fast` или `doubao-seedance-2.0`                         |
| `prompt`   | string | **Обязательно.** Текстовое описание сцены                                    |
| `seconds`  | string | Длительность (сек), **4–15**, например `"5"`, `"10"`                         |
| `metadata` | object | Разрешение, соотношение сторон, входные изображения/видео — см. таблицу ниже |

Поля внутри `metadata`:

| Поле         | Тип       | Описание                                                                                                               |
| ------------ | --------- | ---------------------------------------------------------------------------------------------------------------------- |
| `resolution` | string    | `"480p"` / `"720p"` / `"1080p"`                                                                                        |
| `ratio`      | string    | Соотношение сторон, например `"16:9"`, `"9:16"`, `"1:1"`                                                               |
| `input_type` | string    | Тип входа (обычно можно не указывать — определяется автоматически): `text_to_video` / `first_last_frame` / `reference` |
| `images`     | string\[] | Массив URL изображений (для изображение-в-видео)                                                                       |
| `videos`     | string\[] | Массив URL видео (для референс-видео)                                                                                  |

<Note>
  Чем выше разрешение и длиннее ролик, тем больше токенов и дороже. Если сомневаетесь — начните с `480p` / `5` секунд, а потом настраивайте.
</Note>

## Четыре типа входных данных

`input_type` обычно **указывать не нужно** — он определяется по количеству изображений/видео; при желании задаётся явно через `metadata.input_type`.

| Режим                 | Как передать вход                     | Определяемый `input_type` |
| --------------------- | ------------------------------------- | ------------------------- |
| Текст-в-видео         | только `prompt`                       | `text_to_video`           |
| Изображение-в-видео   | `metadata.images` — **1** изображение | `reference`               |
| Первый-последний кадр | `metadata.images` — **2** изображения | `first_last_frame`        |
| Референс-видео        | `metadata.videos` — **1** видео       | `reference`               |

<Note>
  Изображения / видео должны быть по **публично доступному URL** (сервер должен их скачать); изображения — **JPG / PNG / WebP**, видео — **MP4**. **base64 не поддерживается** (слишком большое тело запроса приведёт к ошибке).
</Note>

Ниже для каждого режима показан **только шаг 1 «Отправить»**; шаги 2 (опрос) и 3 (скачивание) одинаковы для всех режимов.

### Режим 1. Текст-в-видео

Только текстовый `prompt` — генерация целиком по описанию.

<CodeGroup>
  ```bash curl theme={null}
  curl https://www.ruapi.ai/v1/videos \
    -H "Authorization: Bearer sk-ВАШ_КЛЮЧ" \
    -H "Content-Type: application/json" \
    -d '{
      "model": "doubao-seedance-2.0-fast",
      "prompt": "Ночной город, неон отражается на мокром асфальте, киберпанк, камера медленно наезжает",
      "seconds": "5",
      "metadata": { "resolution": "720p", "ratio": "16:9" }
    }'
  ```

  ```python Python theme={null}
  import requests

  resp = requests.post(
      "https://www.ruapi.ai/v1/videos",
      headers={"Authorization": "Bearer sk-ВАШ_КЛЮЧ"},
      json={
          "model": "doubao-seedance-2.0-fast",
          "prompt": "Ночной город, неон отражается на мокром асфальте, киберпанк, камера медленно наезжает",
          "seconds": "5",
          "metadata": {"resolution": "720p", "ratio": "16:9"},
      },
  )
  print(resp.json()["id"])  # получите task id, затем опрашивайте и скачивайте как в полном скрипте выше
  ```
</CodeGroup>

### Режим 2. Изображение-в-видео (1 изображение)

В `metadata.images` — URL **одного** изображения; оно берётся за основу для оживления. В `prompt` опишите нужное движение / работу камеры.

<CodeGroup>
  ```bash curl theme={null}
  curl https://www.ruapi.ai/v1/videos \
    -H "Authorization: Bearer sk-ВАШ_КЛЮЧ" \
    -H "Content-Type: application/json" \
    -d '{
      "model": "doubao-seedance-2.0-fast",
      "prompt": "Человек на фото улыбается и естественно машет рукой, камера медленно наезжает",
      "seconds": "5",
      "metadata": {
        "resolution": "720p",
        "ratio": "16:9",
        "images": ["https://ваш-домен/portrait.jpg"]
      }
    }'
  ```

  ```python Python theme={null}
  import requests

  resp = requests.post(
      "https://www.ruapi.ai/v1/videos",
      headers={"Authorization": "Bearer sk-ВАШ_КЛЮЧ"},
      json={
          "model": "doubao-seedance-2.0-fast",
          "prompt": "Человек на фото улыбается и естественно машет рукой, камера медленно наезжает",
          "seconds": "5",
          "metadata": {
              "resolution": "720p",
              "ratio": "16:9",
              "images": ["https://ваш-домен/portrait.jpg"],
          },
      },
  )
  print(resp.json()["id"])
  ```
</CodeGroup>

### Режим 3. Первый-последний кадр (2 изображения)

В `metadata.images` — **2** изображения: **первое = стартовый кадр, второе = финальный кадр**. Генерируется плавный переход от первого ко второму.

<CodeGroup>
  ```bash curl theme={null}
  curl https://www.ruapi.ai/v1/videos \
    -H "Authorization: Bearer sk-ВАШ_КЛЮЧ" \
    -H "Content-Type: application/json" \
    -d '{
      "model": "doubao-seedance-2.0-fast",
      "prompt": "Плавный переход от первого кадра ко второму, естественное движение камеры, кинематографично",
      "seconds": "5",
      "metadata": {
        "resolution": "720p",
        "ratio": "16:9",
        "images": [
          "https://ваш-домен/first.jpg",
          "https://ваш-домен/last.jpg"
        ]
      }
    }'
  ```

  ```python Python theme={null}
  import requests

  resp = requests.post(
      "https://www.ruapi.ai/v1/videos",
      headers={"Authorization": "Bearer sk-ВАШ_КЛЮЧ"},
      json={
          "model": "doubao-seedance-2.0-fast",
          "prompt": "Плавный переход от первого кадра ко второму, естественное движение камеры, кинематографично",
          "seconds": "5",
          "metadata": {
              "resolution": "720p",
              "ratio": "16:9",
              "images": [
                  "https://ваш-домен/first.jpg",
                  "https://ваш-домен/last.jpg",
              ],
          },
      },
  )
  print(resp.json()["id"])
  ```
</CodeGroup>

### Режим 4. Референс-видео (1 видео)

В `metadata.videos` — URL **одного** короткого видео; модель переосмысливает его, сохраняя **движения объекта** (например, меняет стиль или сцену).

<CodeGroup>
  ```bash curl theme={null}
  curl https://www.ruapi.ai/v1/videos \
    -H "Authorization: Bearer sk-ВАШ_КЛЮЧ" \
    -H "Content-Type: application/json" \
    -d '{
      "model": "doubao-seedance-2.0-fast",
      "prompt": "Сохранить движения человека из видео, сменить стиль на неоновый киберпанк-квартал",
      "seconds": "5",
      "metadata": {
        "resolution": "480p",
        "ratio": "9:16",
        "videos": ["https://ваш-домен/dance.mp4"]
      }
    }'
  ```

  ```python Python theme={null}
  import requests

  resp = requests.post(
      "https://www.ruapi.ai/v1/videos",
      headers={"Authorization": "Bearer sk-ВАШ_КЛЮЧ"},
      json={
          "model": "doubao-seedance-2.0-fast",
          "prompt": "Сохранить движения человека из видео, сменить стиль на неоновый киберпанк-квартал",
          "seconds": "5",
          "metadata": {
              "resolution": "480p",
              "ratio": "9:16",
              "videos": ["https://ваш-домен/dance.mp4"],
          },
      },
  )
  print(resp.json()["id"])
  ```
</CodeGroup>

<Warning>
  **Референс-видео требовательно ко входу**: используйте короткий ролик **длительностью ≤ 15 секунд с чётким объектом (например, человеком)**. Мультфильмы, ролики без явного объекта или слишком длинные видео часто приводят к ошибке. Желательно, чтобы соотношение сторон референса совпадало с целевым `ratio` (например, вертикальный источник → `9:16`).
</Warning>

### Продвинутое: несколько изображений / видео

`images` и `videos` — это **массивы**, в них можно передать сразу несколько референсов (оба варианта проверены):

* **Несколько изображений**: передайте в `images` **3 и более** изображений (официально до 9). Модель объединяет объект / сцену / стиль с нескольких картинок. При 3+ изображениях `input_type` определяется как `reference` автоматически.
* **Несколько видео**: передайте в `videos` **2 и более** роликов (официально до 3, суммарная длительность **≤ 15 секунд**).

<CodeGroup>
  ```bash curl theme={null}
  curl https://www.ruapi.ai/v1/videos \
    -H "Authorization: Bearer sk-ВАШ_КЛЮЧ" \
    -H "Content-Type: application/json" \
    -d '{
      "model": "doubao-seedance-2.0-fast",
      "prompt": "Объедини объект и стиль с этих изображений в цельное видео, естественное движение камеры",
      "seconds": "5",
      "metadata": {
        "resolution": "720p",
        "ratio": "16:9",
        "images": [
          "https://ваш-домен/ref1.jpg",
          "https://ваш-домен/ref2.jpg",
          "https://ваш-домен/ref3.jpg"
        ]
      }
    }'
  ```

  ```python Python theme={null}
  import requests

  resp = requests.post(
      "https://www.ruapi.ai/v1/videos",
      headers={"Authorization": "Bearer sk-ВАШ_КЛЮЧ"},
      json={
          "model": "doubao-seedance-2.0-fast",
          "prompt": "Объедини объект и стиль с этих изображений в цельное видео, естественное движение камеры",
          "seconds": "5",
          "metadata": {
              "resolution": "720p",
              "ratio": "16:9",
              "images": [
                  "https://ваш-домен/ref1.jpg",
                  "https://ваш-домен/ref2.jpg",
                  "https://ваш-домен/ref3.jpg",
              ],
          },
      },
  )
  print(resp.json()["id"])
  ```
</CodeGroup>

<Note>
  С видео аналогично: замените `images` на `videos` и передайте несколько коротких роликов (каждый желательно ≤ 7 секунд с чётким объектом, суммарно ≤ 15 секунд).
</Note>

## Статусы задачи

| `status`      | Значение                                       |
| ------------- | ---------------------------------------------- |
| `queued`      | В очереди                                      |
| `in_progress` | Генерируется                                   |
| `completed`   | Готово, `metadata.url` — ссылка для скачивания |
| `failed`      | Ошибка, причина в поле `error`                 |

## Тарификация

Видео тарифицируется **по токенам** (разрешение × длительность). При отправке списывается **предоплата**, а после завершения сумма пересчитывается по фактическому расходу — разница возвращается. Итог — по фактическому списанию. Цены — на **[странице цен](https://www.ruapi.ai/pricing)**.

## Частые вопросы

<AccordionGroup>
  <Accordion title="Ошибка model_not_found / 404">
    Проверьте две вещи: правильно ли написано имя `model` (`doubao-seedance-2.0-fast`) и верен ли адрес `https://www.ruapi.ai/v1/videos` (с `/v1`).
  </Accordion>

  <Accordion title="Долго висит queued / in_progress">
    Это нормально. Генерация обычно занимает **1–3 минуты**, просто продолжайте опрос и не делайте интервал слишком коротким.
  </Accordion>

  <Accordion title="Скачанный файл пустой / не открывается">
    Скорее всего прошло **более 7 дней** и ссылка истекла. Скачивайте сразу после генерации.
  </Accordion>

  <Accordion title="Задача с референс-видео завершилась ошибкой (failed)">
    Режим требователен ко входу. Убедитесь, что референс-видео **длится ≤ 15 секунд, содержит чёткий объект** и доступно как публичный MP4. Мультфильмы и ролики без явного объекта часто не проходят.
  </Accordion>

  <Accordion title="По какому адресу запрашивать задачу?">
    По маршруту **во множественном числе** `GET /v1/videos/{id}`. Это OpenAI-совместимый формат, и `metadata.url` в ответе сразу является ссылкой для скачивания.
  </Accordion>
</AccordionGroup>

## Дальше

* [Цены и правила тарификации](/ru/pricing)
* Вопросы? [support@ruapi.ai](mailto:support@ruapi.ai)
