Генерация видео Асинхронные задачи Совместимость с OpenAI Медиа-прокси Интеграция API

Интеграция Video Generation API: задачи, опрос и контент

Интегрируйте создание видео с потоками создания/опроса/контента, информацией об изменениях и расширениях, веб-перехватчиками, ограничениями продолжительности и авторизованной доставкой мультимедиа.

AveMujica API 9 мин чтения

Интеграция API с созданием видео — это асинхронный рабочий процесс мультимедиа: вы создаете задание, ждете, пока оно завершится или произойдет сбой, а затем загружаете байты через URL-адрес контента, срок действия которого может истечь и который необходимо авторизовать. В шлюзах, совместимых с OpenAI, которые следуют за поверхностью видео, основными маршрутами являются POST /v1/videos, GET /v1/videos/{task_id} и GET /v1/videos/{task_id}/content. В официальной документации OpenAI теперь сосредоточены редактирование, расширения, символы, веб-перехватчики и Batch наряду с созданием/извлечением, тогда как старая конечная точка remix устарела для новой работы. В этой статье показано, как безопасно интегрировать эти потоки, используя поведение, видимое для репозитория, и официальную документацию, без придуманных задержек или заявлений о цене.

Контекст даты (2026-07-15): OpenAI объявил об прекращении поддержки псевдонимов моделей Videos API и Sora 2 с отключением 2026-09-24 (Прекращение поддержки OpenAI). Не запускайте новый долгосрочный продукт исключительно на Sora 2. Если вы по-прежнему обрабатываете трафик Sora через шлюз, рассматривайте это как окно миграции: продолжайте создавать/опрашивать/контент, избегайте создания нового UX вокруг потоков только ремиксов и планируйте псевдонимы двух поставщиков прямо сейчас.

Прямой ответ: относитесь к видео как к задаче, а не как к завершению чата.

# 1) create
curl -sS https://YOUR_GATEWAY/v1/videos \
  -H "Authorization: Bearer $GATEWAY_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "YOUR_VIDEO_MODEL_ALIAS",
    "prompt": "Slow aerial push-in over a misty cedar forest at dawn",
    "seconds": "4",
    "size": "1280x720"
  }'

# 2) poll (prefer webhooks when the upstream supports them; see below)
curl -sS https://YOUR_GATEWAY/v1/videos/TASK_ID \
  -H "Authorization: Bearer $GATEWAY_KEY"

# 3) download when status=completed
curl -sS https://YOUR_GATEWAY/v1/videos/TASK_ID/content \
  -H "Authorization: Bearer $GATEWAY_KEY" \
  -o forest.mp4

Статусы, которые вы должны обрабатывать явно (как показано в видео DTO этой кодовой базы), включают queued, in_progress, completed и failed. В объекте задачи обычно присутствуют поля id, model, status, progress, created_at, completed_at, expires_at, seconds, size, необязательный error и поля происхождения, такие как remixed_from_video_id, если существует производное задание.

Всегда перепроверяйте матрицы параметров в текущих документах поставщика — OpenAI руководство по созданию видео и Ссылка Videos API. Другие поставщики (видеоповерхности Google Veo/Gemini, Runway, Luma, Kling, ByteDance/Volcengine) публикуют собственные ссылки, в которых могут использоваться другие формы заданий. Шлюз также может предоставлять маршруты, зависящие от поставщика, такие как /v1/video/generations или Kling в стиле /kling/v1/videos/*, в зависимости от адаптеров каналов. Предпочитайте нормализованную задачу в стиле OpenAI API в коде приложения, если шлюз поддерживает ее.

Официальная поверхность OpenAI и то, что сегодня регистрирует этот шлюз

Возможности (документы OpenAI, 2026-07-15)Официальный маршрут/мероприятиеРеальность шлюза в этом репозитории
Создать видеоPOST /v1/videosПоддерживается в качестве основного пути отправки задачи для адаптеров в стиле OpenAI.
Получить/опросGET /v1/videos/{id}Поддерживается
Скачать контентGET /v1/videos/{id}/contentПоддерживается проверками владения
Редактировать существующее видеоPOST /v1/videos/edits (предпочтительно; ремикс устарел)Не нормализован как маршрут шлюза первого класса, установленный сегодня.
Расширить видеоPOST /v1/videos/extensionsНе нормализовано сегодня
ПерсонажиPOST /v1/videos/characters + characters при созданииНе нормализовано сегодня
Наследие ремиксPOST /v1/videos/{id}/remix (не рекомендуется для новых интеграций)По-прежнему обнаруживается/регистрируется в путях в стиле ремикс для существующих адаптеров в стиле Sora.
Вебхукиvideo.completed, video.failedВосходящая функция OpenAI; клиенты шлюза по-прежнему должны реализовывать резервный вариант опроса
BatchBatch API строки до POST /v1/videosФункция восходящего потока; не заменяет таблицы заданий по продуктам

Явно укажите этот пробел в обзорах архитектуры: код продукта, который знает только создание/опрос/контент, выдержит маршрутизацию от нескольких поставщиков; код продукта, который жестко зависит от ремикса, поскольку кнопка «редактировать» будет бороться как с устареванием OpenAI, так и с неполной нормализацией шлюза изменений/расширений/символов.

Почему интеграция видео сложнее, чем интеграция изображений

БеспокойствоИзображения (типичные)Видео (типичное)
Задержкасекундыдесятки секунд до минут
Форма APIчасто один ответсоздать + подождать + контент
Размер полезной нагрузкиКБ–МБнесколько МБ легко
Режимы отказаумеренность/плохой размердлительные тайм-ауты, частичный прогресс, просроченный контент
Ценовой рискn и разрешениепродолжительность, разрешение, редактирование/расширение цепочек
AuthZ после созданиянеобязательнообязательно при загрузке контента

Если вы примените тайм-ауты завершения чата (например, 60s жесткая отмена без опроса), интеграция видео будет выглядеть «нарушенной», даже если задания будут выполнены позже. Создайте таблицу должностей в своем приложении с самого первого дня.

Рекомендуемая модель данных приложения

video_jobs
  id (your id)
  provider_task_id
  model
  prompt_hash / prompt_text (policy-dependent)
  status
  progress
  seconds
  size
  billing_owner_type / billing_owner_id
  team_id / project_id (nullable)
  content_expires_at
  storage_key (nullable until persisted)
  source_task_id (edit/extension/remix lineage)
  last_error
  created_at / updated_at

Рабочие обновляют status и progress с помощью опроса или веб-перехватчика. На completed исполнитель загрузки извлекает /content один раз, сохраняет в хранилище объектов и устанавливает storage_key. На failed используйте error.message/error.code без бесконечных повторов.

Продолжительность и пределы выставления счетов

Продолжительность – это множитель платежа. Этот репозиторий ограничивает продолжительность видео, предоставляемого пользователем, с помощью MaxTaskDurationSeconds = 3600 и отклоняет seconds, выходящий за пределы диапазона, во время проверки. Ваш продукт должен установить более жесткий максимум UX (например, 4–12 секунд для предварительного просмотра), даже если платформа позволяет больше. В официальных примерах создания OpenAI обычно используются дискретные секундные сегменты (включая более длинные варианты 16/20-секунды в текущих документах Sora); никогда не изобретайте бесплатные продолжительности.

Правила интеграции:

  • внимательно разобрать seconds; DTO может передавать его как строку
  • никогда не доверяйте предоставленной клиентом продолжительности отображения цен без повторной проверки сервера.
  • квота предварительного потребления для владельца выставления счетов (пользователя или команды), а не только для исполнителя
  • оплатить или вернуть деньги в случае сбоя задачи после предварительного использования
  • применять ту же дисциплину к цепочкам редактирования/расширения/ремиксов, чтобы пользователи не могли случайно увеличить стоимость

См. мультитенантная архитектура шлюза LLM для разделения владельца и действующего лица и LLM журналы использования и отслеживание затрат для полей атрибуции.

Стратегия ожидания: сначала веб-перехватчики, опрос в качестве запасного варианта

Видеоруководство OpenAI рекомендует выполнять опрос примерно каждые 10–20 секунд с отсрочкой и предпочитает веб-перехватчики (video.completed / video.failed), если они доступны. URL-адреса загрузки документированы как недолговечные (около 1 часа после создания в руководстве OpenAI) — немедленно скопируйте их в свое хранилище.

Практические настройки по умолчанию для работников продукта:

  1. Зарегистрируйте веб-перехватчики, если поставщик и ваш шлюз/путь оператора поддерживают подписанную доставку.
  2. Опрос в качестве страховки: начните с 10s, добавьте джиттер, отступите в сторону 20–30s под нагрузкой или повторите in_progress.
  3. Уважайте Retry-After, если он присутствует.
  4. Ограничить общее время ожидания с помощью жесткого тайм-аута и локального состояния терминала expired/failed.
  5. Никогда не опрашивайте каждые несколько сотен миллисекунд для каждой вкладки браузера.
type VideoTask = {
  id: string;
  status: "queued" | "in_progress" | "completed" | "failed" | string;
  progress?: number;
  expires_at?: number;
  error?: { message?: string; code?: string };
};

async function sleep(ms: number) {
  await new Promise((r) => setTimeout(r, ms));
}

async function pollVideo(taskId: string, timeoutMs = 15 * 60_000): Promise<VideoTask> {
  const started = Date.now();
  let interval = 10_000;
  while (Date.now() - started < timeoutMs) {
    const res = await fetch(`${process.env.GATEWAY_BASE}/v1/videos/${taskId}`, {
      headers: { Authorization: `Bearer ${process.env.GATEWAY_KEY}` },
    });
    if (res.status === 429) {
      const ra = Number(res.headers.get("retry-after"));
      await sleep(Number.isFinite(ra) ? ra * 1000 : interval);
      interval = Math.min(interval + 5_000, 30_000);
      continue;
    }
    if (!res.ok) throw new Error(await res.text());
    const task = (await res.json()) as VideoTask;
    if (task.status === "completed" || task.status === "failed") return task;
    const jitter = Math.floor(Math.random() * 2_000);
    await sleep(interval + jitter);
    interval = Math.min(Math.floor(interval * 1.2), 30_000);
  }
  throw new Error("video poll timeout");
}

Настраивайтесь на основе измеренных сроков завершения для ваших моделей и региона, а не на основе сообщений в блоге другой команды.

AuthZ для загрузки контента и области рабочей среды

Создание задачи — это не то же самое, что возможность позже передать ее байты в потоковом режиме. В мультитенантных шлюзах /v1/videos/{id}/content должен обеспечивать право собственности: ту же область пользователя/команды/проекта, которая создала задание (или явную политику общего доступа). Угадывание идентификатора задачи между арендаторами должно завершиться неудачно.

Пути к рабочей среде в этом репозитории:

  • Пользовательский интерфейс: видео верстак
  • личные API под /api/user/video-workbench
  • команда API под /api/teams/:team_id/video-workbench с действиями в рамках проекта
  • отдельные гранты, такие как создание видео и управление видеоресурсами.

Это отличается от только личного рабочий стол для изображений. Если для надежного воспроизведения в рабочей среде требуется хранилище объектов, настройте его, прежде чем обещать постоянную историю. Резервные URL-адреса воспроизведения, указывающие на /v1/videos/{id}/content, по-прежнему требуют активной аутентификации Z и могут подпадать под действие expires_at.

Правки, расширения, персонажи и устаревшие ремиксы

Официальное руководство OpenAI по новым интеграциям:

  • Изменения: POST /v1/videos/edits с подсказкой и исходным кодом video для целевых изменений; ремикс устарел для этой работы.
  • Расширения: POST /v1/videos/extensions для продолжения завершенного клипа (сшитая общая продолжительность; символы не поддерживаются в расширениях согласно руководству OpenAI).
  • Символы: POST /v1/videos/characters, затем для обеспечения единообразия укажите идентификаторы персонажей при создании.
  • Batch: автономные очереди линий POST /v1/videos JSON; Пакетные выходные данные имеют собственный период хранения в документах OpenAI.

Советы по интеграции, которые по-прежнему применимы к любому производному заданию (включая устаревший ремикс, который все еще присутствует в этом шлюзе):

  • разрешать производные задания только тогда, когда вызывающий может прочитать исходную задачу
  • копировать поля аренды из источника; не оставляйте деривативы не под тем проектом
  • показать пользователям, что редактирование/расширение/ремикс — это новая оплачиваемая работа, а не бесплатная настройка.
  • persist lineage для поддержки и модерации
  • пометка функции для любого пакета метаданных, предназначенного только для поставщика; проверить продолжительность/размер с глобальными границами

Пока шлюз не нормализует изменения/расширения/символы, храните эти вызовы за явными флагами адаптера или собственными восходящими клиентами — не притворяйтесь, что ремикс — это современный путь OpenAI.

Политика сохранения

Предположим:

  1. URL-адреса исходящего контента и даже временные прокси-серверы шлюза могут истечь (expires_at — поле первого класса; документы OpenAI ~1 час для интерактивных загрузок)
  2. страницам продуктов нужны ваши ключи объекта
  3. миниатюры создаются после загрузки, а не специально извлекаются из CDN провайдера.
  4. удаление должно быть возможным, когда команда уходит или пользователь реализует права хранения.

Безопасный трубопровод:

completed → авторизованная выборка контента → анализ вирусов/типов, если требуется → размещение объекта в хранилище → БД storage_key → обслуживание через CDN с аутентификацией приложения.

Пропуск хранилища «пока оно нам не понадобится» — вот как демо-версии становятся записками об инцидентах, что особенно болезненно, если сам восходящий Videos API выходит из строя.

Наблюдаемость и поддержка

Зарегистрируйте как минимум идентификатор запроса шлюза или идентификатор задачи, псевдоним модели, секунды, размер, переходы состояний, владельца и участника выставления счетов, путь веб-перехватчика и опроса и окончательный код ошибки. Панели мониторинга должны отделять классы сбоев видео от сбоев чата. Инструменты поддержки должны открывать журнал задач и использования без загрузки полного MP4 в систему заявок.

Альтернативные маршруты, с которыми вы можете столкнуться

В зависимости от адаптеров каналов операторы также могут включать:

  • Конечные точки в стиле /v1/video/generations
  • Kling /kling/v1/videos/*
  • Адаптеры задач Gemini/Vertex Veo
  • другая задача поставщика API за Джимэном или аналогичными маршрутами

Команды приложений не должны жестко запрограммировать путь каждого поставщика. Предпочитайте один нормализованный клиент (/v1/videos + стабильные псевдонимы) и позвольте шлюзу сопоставлять каналы. Если функция существует только в пути поставщика (кисти движения, настройки кино), изолируйте ее с помощью флага функции и задокументируйте непереносимый контракт.

Связанное чтение

Источники

Оперативные вопросы и ответы

Могу ли я заблокировать запрос HTTP, пока видео не будет готово?

Только для коротких внутренних инструментов. Пользовательские интерфейсы продукта должны создавать запись о задании и использовать веб-перехватчики или опросы. Длинные синхронные запросы увеличивают время ожидания шлюза и балансировщика нагрузки.

Какой интервал опроса мне следует использовать?

По умолчанию около 10 секунд с джиттером, отступите к 20–30 секунд, соблюдайте Retry-After и отдавайте предпочтение веб-перехватчикам video.completed/video.failed, если они доступны. В руководстве OpenAI цитируется примерно второй опрос 10–20.

Почему загрузка контента не удалась после завершения статуса?

Распространенные причины: просроченный контент, неправильная область аутентификации, задача, принадлежащая другому проекту, или неправильная конфигурация хранилища/прокси. Прежде чем повторить попытку создания, проверьте expires_at и поля аренды.

Должны ли новые продукты использовать ремикс?

Нет в качестве основного пути редактирования. Официальная документация OpenAI направляет новую работу по редактированию в POST /v1/videos/edits; ремикс устарел. Этот шлюз по-прежнему может принимать маршруты в стиле ремиксов для совместимости — рассматривайте это как устаревший мост, а не как новую разработку.

Нужна ли мне рабочая среда для видео, если я уже звоню по /v1/videos?

Нет для чистых серверных конвейеров. Да, когда людям нужна общая история, настройки или управление ресурсами команды в пользовательском интерфейсе.

Первый рабочий, отправивший товар

Реализуйте один рабочий процесс, который создает короткое видео с помощью стабильного псевдонима, отличного от Sora, если он у вас есть, или явно временного псевдонима Sora с записанной датой миграции до 2026-09-24. Опросите с помощью 10s+jitter (вебхук необязательно), загрузите /content один раз, загрузите в хранилище объектов и докажите, что ключ второй команды не может загрузить идентификатор задачи. Только после этого подключите счастливый путь к пользовательскому интерфейсу продукта.