MiniMax Hailuo
Hailuo — семейство генерации видео от MiniMax. Один канал обслуживает два поколения API: MiniMax-H3 и MiniMax-H3-Max работают через API /v2 MiniMax с массивом content и рассчитываются по секундам, а семейство MiniMax-Hailuo-2.3 использует старый API /v1 с фиксированной ценой за задачу (описано в конце страницы).
Задачи отправляются, опрашиваются и скачиваются через общие эндпоинты из разделов Создание задачи и Получение задачи. На этой странице описано, что читает адаптер этого провайдера, как собирается запрос и как он тарифицируется.
Модели
Section titled “Модели”| ID модели | Разрешения | Длительность (целые секунды) | По умолчанию | Расширение промпта |
|---|---|---|---|---|
MiniMax-H3 | 768P, 2K | 4–15 | 768P, 5 с | Нет |
MiniMax-H3-Max | 480P, 768P | 5–15 | 768P, 5 с | Да |
- ID модели чувствителен к регистру: указывайте его так, как в таблице. Аккаунту доступны только модели, направленные на него, и цена зависит от аккаунта;
GET /v1/models— авторитетный список для вашего ключа. extraпринимает толькоMiniMax-H3-Max. ПередачаextraвMiniMax-H3возвращает400.- Обе модели поддерживают текст-в-видео, первый кадр, первый и последний кадры, а также референсные изображения, видео и аудио.
Параметры запроса
Section titled “Параметры запроса”| Поле | Тип | Обязательно | По умолчанию | Описание |
|---|---|---|---|---|
model | string | Да | — | ID модели из GET /v1/models |
prompt | string | Да | — | Промпт; пустой после обрезки пробелов отклоняется. До 7000 символов |
resolution | string | Нет | 768P | Без учёта регистра; должен быть одним из разрешений модели |
duration | integer | Нет | 5 | Целые секунды в диапазоне модели |
seconds | string | Нет | — | Строковая форма длительности; читается, только если duration нет или он 0 |
ratio | string | Нет | см. ниже | Соотношение сторон |
images | string[] | Нет | — | 1 изображение = первый кадр, 2 = сначала первый, затем последний. Не более 2 |
image | string | Нет | — | Одно изображение; используется, только если images пуст |
metadata | object | Нет | — | Параметры MiniMax, см. следующий раздел |
Правила приоритета:
metadata.resolution,metadata.durationиmetadata.ratioпереопределяют одноимённые поля верхнего уровня.secondsчитается, только еслиdurationверхнего уровня отсутствует или равен0, аmetadata.durationимеет приоритет над обоими.metadata.durationразбирается как число, поэтому5.5даётinvalid duration. В отличие отdurationверхнего уровня,0здесь означает не «не задано», а выход за диапазон. Чтобы сохранить значение по умолчанию, просто не передавайте ключ.sizeне поддерживается.sizeверхнего уровня илиmetadata.sizeвозвращаетMiniMax-H3 请使用 resolution(480P/768P/2K),不支持 size; используйтеresolution.- Помимо
size, поля верхнего уровня, которые этот провайдер не читает (напримерgenerate_audioилиinput_reference), игнорируются, а не отклоняются.
Параметры metadata
Section titled “Параметры metadata”| Поле | Тип | Описание |
|---|---|---|
content | array | Входной материал, см. Элементы content и ограничения. Несовместим с images / image верхнего уровня |
resolution | string | Переопределяет resolution верхнего уровня |
duration | number | Переопределяет duration и seconds верхнего уровня; должно быть целым числом в диапазоне |
ratio | string | Переопределяет ratio верхнего уровня |
aigc_watermark | boolean или string | true / false. Строки "true" / "false" тоже принимаются — именно их отправляют multipart-формы. Если не передано, решает провайдер |
extra.prompt_expansion_mode | string | disabled, balanced или quality. Только MiniMax-H3-Max |
size | — | Отклоняется с 400 |
metadata декодируется в типизированную структуру: неверный тип JSON для одного из ключей выше (например "duration": "abc" или content в виде объекта) возвращает 400 с сообщением invalid metadata: ..., и списание не производится. Ключи, которых нет в таблице — seed, callback_url и прочие — игнорируются и до MiniMax не доходят; callback не отправляется, результат нужно опрашивать.
Соотношение сторон ratio
Section titled “Соотношение сторон ratio”Допустимые значения: adaptive, 21:9, 16:9, 4:3, 1:1, 3:4, 9:16. Регистр не важен.
| Форма запроса | Без ratio | Правила |
|---|---|---|
| Только текст (без кадров и референсов) | 16:9 | adaptive отклоняется с text-to-video does not support ratio adaptive |
| Первый кадр или первый и последний | adaptive | Принудительно adaptive; переданное значение игнорируется и не проверяется |
| Референсный материал | adaptive | Любое из семи значений |
Элементы content и ограничения
Section titled “Элементы content и ограничения”metadata.content — упорядоченный массив. У каждого элемента есть type, поле полезной нагрузки для этого типа и необязательный role:
type | Полезная нагрузка | Допустимые role | Лимит |
|---|---|---|---|
text | text | нет | 1, и должен совпадать с prompt |
image_url | image_url.url | first_frame | 1 |
image_url | image_url.url | last_frame | 1, и требуется first_frame |
image_url | image_url.url | reference_image | 9 |
image_url | image_url.url | нет | только как единственный материал |
video_url | video_url.url | reference_video (обязателен) | 3 |
audio_url | audio_url.url | reference_audio (обязателен) | 3 |
{ "type": "image_url", "role": "reference_image", "image_url": { "url": "https://..." } }{ "type": "video_url", "role": "reference_video", "video_url": { "url": "https://..." } }{ "type": "audio_url", "role": "reference_audio", "audio_url": { "url": "https://..." } }Проверки перед отправкой запроса:
- Не более 12 материалов на запрос, из них не более 9 референсных изображений, 3 референсных видео и 3 референсных аудио.
- Кадры первого / последнего кадра и референсный материал нельзя смешивать.
reference_image,reference_videoиreference_audioсвободно комбинируются. - Элемент
image_urlбезroleдопустим, только если это единственный материал; тогда он считаетсяfirst_frame. - Если в
contentнет элементаtext, RouteAPI добавляет в начало элемент с текстом изpromptверхнего уровня. Если он есть, он должен быть один, а его текст должен совпадать сpromptпосле обрезки пробелов, иначе запрос падает сprompt 与 metadata.content 中的 text 冲突. contentиimages/imageверхнего уровня взаимоисключающие.- Передаётся только поле, соответствующее
typeэлемента; лишние ключи отбрасываются. - URL материалов — включая
images/imageверхнего уровня — должны бытьhttp://,https://илиdata:URI (напримерdata:image/png;base64,...) и скачиваться без авторизации. Идентификаторы файлов MiniMax (mm_file://) не поддерживаются. URL, которые MiniMax цитирует в отказе, заменяются на[url omitted], поэтому подписанные ссылки на материалы не попадают в сообщения об ошибках. - Ограничения формата, размеров, длительности и объёма каждого материала задаёт MiniMax; RouteAPI их не проверяет. Неподходящий материал либо отклоняется при отправке (
400, списания нет), либо отклоняется в процессе генерации (задача становитсяFAILURE, резерв возвращается).
Примеры
Section titled “Примеры”Текст в видео
Section titled “Текст в видео”curl https://api.routeapi.ai/v1/video/generations \ -H "Authorization: Bearer $ROUTEAPI_KEY" \ -H "Content-Type: application/json" \ -d '{ "model": "MiniMax-H3", "prompt": "A paper boat drifting down a rain-soaked street, cinematic lighting", "resolution": "768P", "ratio": "16:9", "duration": 5 }'Первый кадр
Section titled “Первый кадр”curl https://api.routeapi.ai/v1/video/generations \ -H "Authorization: Bearer $ROUTEAPI_KEY" \ -H "Content-Type: application/json" \ -d '{ "model": "MiniMax-H3", "prompt": "The camera slowly pushes in as the subject looks up and smiles", "images": ["https://cdn.example.com/first.jpg"], "resolution": "768P", "duration": 5 }'Первый и последний кадр
Section titled “Первый и последний кадр”Две записи в images становятся first_frame и last_frame. ratio принудительно равен adaptive.
curl https://api.routeapi.ai/v1/video/generations \ -H "Authorization: Bearer $ROUTEAPI_KEY" \ -H "Content-Type: application/json" \ -d '{ "model": "MiniMax-H3", "prompt": "The scene transitions from morning to sunset while the camera pans smoothly", "images": [ "https://cdn.example.com/first.jpg", "https://cdn.example.com/last.jpg" ], "resolution": "768P", "duration": 5 }'Референсные изображения, видео и аудио
Section titled “Референсные изображения, видео и аудио”metadata.content нужен, когда требуется больше двух изображений или референсное видео / аудио. Референсное видео тарифицируется, поэтому держите его длительность в пределах 2–15 секунд — см. Оплата.
curl https://api.routeapi.ai/v1/video/generations \ -H "Authorization: Bearer $ROUTEAPI_KEY" \ -H "Content-Type: application/json" \ -d '{ "model": "MiniMax-H3", "prompt": "The character in the image dances to the rhythm of the reference audio, copying the motion of the reference video", "resolution": "768P", "ratio": "9:16", "duration": 8, "metadata": { "content": [ { "type": "image_url", "role": "reference_image", "image_url": { "url": "https://cdn.example.com/character.jpg" } }, { "type": "video_url", "role": "reference_video", "video_url": { "url": "https://cdn.example.com/motion.mp4" } }, { "type": "audio_url", "role": "reference_audio", "audio_url": { "url": "https://cdn.example.com/music.mp3" } } ] } }'Расширение промпта и водяной знак H3-Max
Section titled “Расширение промпта и водяной знак H3-Max”curl https://api.routeapi.ai/v1/video/generations \ -H "Authorization: Bearer $ROUTEAPI_KEY" \ -H "Content-Type: application/json" \ -d '{ "model": "MiniMax-H3-Max", "prompt": "A rainy city street at night, neon signs reflected in puddles", "resolution": "480P", "duration": 6, "metadata": { "aigc_watermark": false, "extra": { "prompt_expansion_mode": "quality" } } }'Статус и результат задачи
Section titled “Статус и результат задачи”Соответствие статусов
Section titled “Соответствие статусов”task.status MiniMax | data.status | data.progress |
|---|---|---|
queued | QUEUED | 20% |
running | IN_PROGRESS | 50% |
succeeded с content.url | SUCCESS | 100% |
succeeded без content.url | FAILURE | 100% |
failed, cancelled | FAILURE | 100% |
| любое другое значение | IN_PROGRESS | 30% |
Задача succeeded без URL видео считается неуспешной с fail_reason upstream succeeded without video url, и резерв возвращается. Для failed или cancelled в fail_reason попадает task.error.message от MiniMax (все URL заменяются на [url omitted]); если сообщения нет, причина — task failed или task cancelled.
Если ответ опроса — конверт ошибки ({"type":"error","error":{...}}), этот цикл опроса завершается ошибкой, и задача опрашивается снова. Тело без объекта задачи разбирается по старой схеме /v1, которая пуста, поэтому задача просто остаётся в IN_PROGRESS. Задача, которая так и не достигла терминального состояния, помечается как неуспешная по таймауту платформы — по умолчанию 24 часа — с fail_reason 任务超时(1440分钟), и резерв возвращается.
Запись задачи
Section titled “Запись задачи”GET /v1/video/generations/{task_id} возвращает строку задачи RouteAPI; все поля описаны в разделе Получение задачи. Для этого провайдера полезны:
| Поле | Описание |
|---|---|
data.status / data.progress | Состояние и прогресс задачи из таблицы выше |
data.result_url | URL видео после успешного завершения |
data.fail_reason | Причина сбоя, иначе пусто |
data.quota | Списано квоты за эту задачу |
data.properties.input | Снимок запроса, отправленного провайдеру; URL материалов заменены на [omitted, N bytes]. Полезен при споре о списании |
data.data | Последний ответ MiniMax |
{ "code": "success", "message": "", "data": { "task_id": "task_FQvcRkHE9wjSWwyISDcrWCKoqCPNdkCx", "platform": "35", "group": "default", "action": "generate", "status": "SUCCESS", "progress": "100%", "fail_reason": "", "result_url": "https://cdn.minimax.example/video/424010985738629.mp4?Expires=...", "submit_time": 1792412645, "start_time": 1792412650, "finish_time": 1792412780, "data": { "task": { "id": "424010985738629", "status": "succeeded", "content": { "url": "https://cdn.minimax.example/video/424010985738629.mp4?Expires=..." }, "resolution": "768P", "usage": { "output_seconds": 5, "input_seconds": 0, "input_image_count": 1 } } } }}Полезные внутренние поля:
| Поле | Описание |
|---|---|
data.data.task.id | ID задачи MiniMax, отличается от task_id RouteAPI |
data.data.task.status | queued, running, succeeded, failed или cancelled |
data.data.task.content.url | URL видео при успехе; именно он попадает в result_url |
data.data.task.resolution | Разрешение, которое сообщает MiniMax. Тарификация идёт по запрошенному, не по нему |
data.data.task.usage.output_seconds | Длительность полученного видео, используется при расчёте |
data.data.task.usage.input_seconds | Длительность референсного видео, используется при расчёте |
data.data.task.usage.input_image_count | Число изображений от MiniMax; расчёт использует число из запроса |
data.data.task.error.code / .message | Детали сбоя, если MiniMax их сообщает |
До первого успешного опроса data.data — это сырой ответ на отправку ({"task_id": "..."}), поля task в нём нет. task.usage появляется, когда MiniMax его возвращает, обычно при успехе. Всегда ориентируйтесь на внешний data.status.
Скачивание видео
Section titled “Скачивание видео”data.result_url уже указывает на CDN MiniMax. Ссылка истекает по расписанию MiniMax, поэтому скачивайте сразу, как только задача перешла в SUCCESS.
- Прямая ссылка CDN: запрашивайте без заголовка
Authorization; некоторые хранилища отклоняют лишние заголовки авторизации. https://api.routeapi.ai/v1/videos/{task_id}/content: передаёт ту же сохранённую ссылку через RouteAPI и требуетAuthorization: Bearer $ROUTEAPI_KEY. Он каждый раз заново запрашивает сохранённую ссылку, поэтому срок действия не продлевается. Нужен, когда клиент не должен видеть хост провайдера или CDN отказывает в прямом доступе. Возвращает404 Task not foundдля неизвестной задачи и400 Task is not completed yet, current status: ..., пока задача не завершилась успешно.
# direct CDN linkcurl -L -o out.mp4 "$RESULT_URL"# RouteAPI proxycurl -L -o out.mp4 -H "Authorization: Bearer $ROUTEAPI_KEY" \ "https://api.routeapi.ai/v1/videos/$TASK_ID/content"Оплата
Section titled “Оплата”Оплата по секундам действует, когда для модели в вашем аккаунте задана фиксированная цена (её показывает страница модели в консоли). Если модель тарифицируется только по коэффициенту, действует обычное списание за задачу, и расчёта по завершении нет. При оплате по секундам сумма складывается из трёх частей:
| Компонент | Цена за единицу | Учитывается при отправке (резерв) | Учитывается при расчёте |
|---|---|---|---|
| Выходное видео | за секунду, для запрошенного разрешения | запрошенный duration | min(usage.output_seconds, duration) |
| Входное референсное видео | за секунду, для запрошенного разрешения | 15 с, если в content есть reference_video | usage.input_seconds, действует только в диапазоне 2–15 с |
| Изображения | за изображение сверх бесплатного лимита | все элементы image в собранном content, включая кадры | то же число из снимка запроса |
Цены и бесплатный лимит изображений настраиваются для аккаунта; встроенные значения — 5 бесплатных изображений для MiniMax-H3 и 2 для MiniMax-H3-Max, но консоль главнее. На этой странице цены не приводятся.
| Момент | Секунды выхода | Секунды референсного видео |
|---|---|---|
| Резерв при отправке | запрошенный duration | 15 с, если в запросе есть референсное видео |
| Расчёт при успехе | usage.output_seconds, но не больше запрошенного duration | usage.input_seconds, если он в пределах 2–15 с |
Правила:
- Расчёт только возвращает: итоговое списание — меньшее из пересчитанной суммы и резерва.
- Расчёт использует цены, зафиксированные при отправке. Изменение цен во время выполнения на задачу не влияет.
- Без референсного видео компонента входных секунд нет вовсе, а
usage.input_secondsигнорируется. - Референсное аудио бесплатно, компонент изображений при расчёте не меняется.
- Поскольку запрос с референсным видео резервирует 15 секунд входа, баланс должен покрывать этот худший случай, даже если видео короче.
- Если
usageотсутствует,output_secondsравен0или больше 15, либо (при наличии референсного видео)input_secondsотсутствует или вне 2–15 — RouteAPI сохраняет весь резерв и ничего не возвращает. Держите референсные видео в пределах 2–15 секунд, чтобы этого избежать. - Неуспешная или просроченная задача возвращает весь резерв; запрос, отклонённый с
400, не тарифицируется. - При оплате по секундам заголовок
X-New-Api-Other-Ratiosответа на отправку содержит множитель к цене модели в ключеh3_units(для задачи 5 с в768Pэто{"h3_units": 5}). Для семейства 2.3 и для модели H3 без фиксированной цены он равен{}.
Пример расчёта
Section titled “Пример расчёта”Цены ниже гипотетические и приведены только для арифметики: MiniMax-H3 в 768P стоит $0.10 за секунду выхода, $0.10 за секунду референсного видео и $0.04 за изображение сверх 5 бесплатных. Запрос на 10 секунд с двумя референсными изображениями и одним референсным видео:
- Резерв: 10 × 0.10 (выход) + 15 × 0.10 (референсное видео по пределу) + max(0, 2 − 5) × 0.04 (изображения) = $2.50.
- MiniMax вернул
output_seconds: 8иinput_seconds: 6: 8 × 0.10 + 6 × 0.10 + 0 = $1.40. - Разница $1.10 возвращается на баланс.
Ошибки
Section titled “Ошибки”Отправка полностью проверяется до резервирования, поэтому 400 ничего не стоит. Бизнес-отказы MiniMax приходят внутри ответа HTTP 200 и преобразуются так:
base_resp.status_code MiniMax | Значение | HTTP вам | code |
|---|---|---|---|
1026 | Отказ по содержимому / цензуре | 400 | 1026 |
2013 | Ошибка параметра | 400 | 2013 |
1002 | Превышен лимит запросов | 429 | 1002 |
1004, 2049 | Сбой ключа / авторизации у провайдера | 401, обычно возвращается как 503 | 1004 / 2049 или get_channel_failed |
1008 | Исчерпан баланс у провайдера | 503 | get_channel_failed |
| любой другой код | Неизвестная бизнес-ошибка | 502 | числовой код |
— (тело не разбирается или конверт type: "error") | Некорректный ответ на отправку | 502 | invalid_response |
— (пустой task_id) | Провайдер не вернул ID задачи | 502 | upstream_task_id_missing |
Сбои аккаунта провайдера не передаются дословно. Адаптер преобразует 1008 в 402, а 1004 / 2049 — в 401; затем RouteAPI классифицирует сбой как сбой канала и отвечает 503 get_channel_failed с общим сообщением «сервис провайдера временно недоступен», предварительно попробовав другой канал, если он есть. 402 от 1008 по той же причине приходит как 503. В этих случаях status_msg MiniMax до вас не доходит. 429 сохраняет статус, но сообщение заменяется общим уведомлением о перегрузке. В 400 попадает текст MiniMax с префиксом hailuo api error: .
Если MiniMax отвечает статусом HTTP, отличным от 200, тело не разбирается: вы получаете код fail_to_fetch_task с этим статусом. Опрос неизвестного task_id или задачи другого аккаунта возвращает 400 с кодом task_not_exist.
Ошибки, возникающие до попадания запроса в MiniMax, подчиняются общим правилам из раздела Частые ошибки: 401 при отсутствующем или неверном API Key, 403 insufficient_user_quota, если баланс не покрывает резерв (включая худший случай с 15 секундами референсного видео), и 403 с This token has no access to model ..., если ключу не разрешена эта модель.
Частые сообщения 400 (код invalid_request, если не указано иное):
message | Причина |
|---|---|
prompt is required | prompt отсутствует или пуст |
seconds must be between 1 and 3600 (код invalid_seconds) | duration верхнего уровня отрицателен или больше 3600 |
invalid seconds: abc | seconds не является строкой с целым числом |
<model> 请使用 resolution(480P/768P/2K),不支持 size | size передан на верхнем уровне или в metadata; в сообщении имя вашей модели, а список разрешений всегда 480P/768P/2K |
invalid resolution: 1080P, MiniMax-H3 supports 768P, 2K | Разрешение не поддерживается этой моделью |
invalid duration: 3, MiniMax-H3 supports integer 4-15 | Длительность ниже минимума, больше 15 или не целая |
invalid ratio: 2:1, supports adaptive, 21:9, 16:9, 4:3, 1:1, 3:4, 9:16 | Ratio отсутствует в списке |
text-to-video does not support ratio adaptive | adaptive в запросе без кадров и референсов |
at most 2 top-level images (first_frame, last_frame), got 3; use metadata.content for reference media | Больше 2 записей в images |
images must not contain empty values | Пустая запись в images |
metadata.content cannot be combined with top-level images | Переданы оба |
metadata.content must be a non-empty array | content равен [] |
prompt 与 metadata.content 中的 text 冲突 | Элемент text не совпадает с prompt |
metadata.content accepts at most one text item | Больше одного элемента text |
text exceeds 7000 characters | Промпт длиннее 7000 символов |
invalid content type "foo" | Неизвестный type |
invalid role "foo" for image_url | Неизвестный role изображения |
image_url without role is only allowed as the single input image | Изображение без role вместе с другими материалами |
last_frame requires first_frame | Передан только последний кадр |
at most one first_frame and one last_frame | Дублирующиеся роли кадров |
first/last frame images cannot be combined with reference media | Кадры смешаны с референсным материалом |
at most 9 reference images / at most 3 reference videos / at most 3 reference audios / at most 12 media items | Превышен лимит по типу или общий лимит материалов |
video_url requires role reference_video / audio_url requires role reference_audio | Неверный или отсутствующий role для этого типа |
image_url.url must be an http(s) URL or data URI (то же для video_url / audio_url) | Неподдерживаемая схема URL, включая mm_file:// |
MiniMax-H3 does not support extra | metadata.extra передан модели, отличной от Max |
invalid extra.prompt_expansion_mode: balance, supports disabled, balanced, quality | Неизвестный режим расширения |
invalid metadata: ... | Неверный тип JSON у ключа metadata |
Сбои после успешной отправки — модерация содержимого, недоступный материал, отменённая или просроченная задача — никогда не проявляются как ошибки HTTP. Они отображаются в записи задачи как FAILURE с fail_reason, и резерв возвращается.
Отличия от API MiniMax
Section titled “Отличия от API MiniMax”- Пути принадлежат RouteAPI:
POST /v1/video/generationsиGET /v1/video/generations/{task_id}. Эндпоинты MiniMax/v2/video_generationи/v2/query/video_generation/{id}не предоставляются, поэтому замена Base URL в официальном SDK не поможет. - Промпт передаётся в
promptверхнего уровня, а массивcontentMiniMax — вmetadata.content. RouteAPI собираетcontentдля провайдера, включая элемент text, а ярлыки первого / последнего кадра черезimagesу MiniMax отсутствуют. - Полученный
task_idпринадлежит RouteAPI. ID задачи MiniMax виден только вdata.data.task.id. - RouteAPI проверяет типы элементов, роли, количество и схемы URL перед отправкой — строже, чем MiniMax, который большую часть оставляет этапу генерации.
- Передаются только
model,content,resolution,duration,ratio,aigc_watermarkиextra. Остальные параметры MiniMax, включаяcallback_url, отбрасываются. - Материалы должны быть публичными
http(s)илиdata:URL; идентификаторы файловmm_file://использовать нельзя. - При отсутствии
resolutionиdurationRouteAPI подставляет768Pи 5 секунд, поэтому провайдер всегда получает явные значения. - При успехе RouteAPI сохраняет
content.urlMiniMax какresult_url; отдельного этапа получения файла вызывать не нужно.
Полный скрипт опроса
Section titled “Полный скрипт опроса”Нужны bash, curl и jq. Скрипт отправляет задачу текст-в-видео на 5 секунд, опрашивает её каждые 15 секунд до 30 минут, скачивает результат (заголовок Authorization добавляется только для прокси-формы RouteAPI) и печатает тарифицируемый usage.
#!/usr/bin/env bashset -euo pipefail
: "${ROUTEAPI_KEY:?export ROUTEAPI_KEY first}"BASE="${ROUTEAPI_BASE:-https://api.routeapi.ai}"AUTH="Authorization: Bearer $ROUTEAPI_KEY"
TASK_ID=$(curl -sS -X POST "$BASE/v1/video/generations" \ -H "$AUTH" -H "Content-Type: application/json" \ -d '{ "model": "MiniMax-H3", "prompt": "A paper boat drifting down a rain-soaked street, cinematic lighting", "resolution": "768P", "ratio": "16:9", "duration": 5 }' | jq -er '.task_id')
echo "task: $TASK_ID"
for _ in $(seq 1 120); do RESP=$(curl -sS "$BASE/v1/video/generations/$TASK_ID" -H "$AUTH") STATUS=$(jq -r '.data.status // empty' <<<"$RESP") echo "status: ${STATUS:-unknown} $(jq -r '.data.progress // ""' <<<"$RESP")"
case "$STATUS" in SUCCESS) URL=$(jq -r '.data.result_url' <<<"$RESP") OUT="$TASK_ID.mp4" if [[ "$URL" == *"/v1/videos/"*"/content" ]]; then curl -sSL -o "$OUT" -H "$AUTH" "$URL" else curl -sSL -o "$OUT" "$URL" fi echo "saved: $OUT" jq -r '.data.data.task.usage // {}' <<<"$RESP" exit 0 ;; FAILURE) echo "failed: $(jq -r '.data.fail_reason' <<<"$RESP")" >&2 exit 1 ;; esac
sleep 15done
echo "gave up after 30 minutes" >&2exit 1MiniMax-Hailuo-2.3
Section titled “MiniMax-Hailuo-2.3”MiniMax-Hailuo-2.3 и MiniMax-Hailuo-2.3-Fast работают через API /v1/video_generation MiniMax и тарифицируются за задачу, а не по секундам. RouteAPI отправляет запрос, опрашивает /v1/query/video_generation, затем получает результат через /v1/files/retrieve MiniMax и сохраняет ссылку на скачивание в result_url.
| ID модели | Примечания |
|---|---|
MiniMax-Hailuo-2.3 | Текст-в-видео и изображение-в-видео |
MiniMax-Hailuo-2.3-Fast | Более быстрый и дешёвый вариант 2.3 |
Обе по умолчанию используют 768P и 6 секунд. API задач не проверяет разрешение и длительность этого семейства сверх общего лимита 0–3600: значения передаются как есть, решает MiniMax. Playground в консоли предлагает 768P / 1080P и 6 или 10 секунд, причём 1080P ограничен 6 секундами.
Как отображается запрос (2.3)
Section titled “Как отображается запрос (2.3)”| Поле конверта | Что делает адаптер |
|---|---|
prompt | Отправляется как prompt; metadata.prompt переопределяет его |
duration | Отправляется как duration; отсутствие или 0 превращается в 6 |
size | Преобразуется в resolution по подстроке: 1080 → 1080P, 768 → 768P, 720 → 720P, 512 → 512P; иначе — значение по умолчанию модели |
images / image | Не читаются. Входное изображение передаётся только через metadata.first_frame_image |
ratio, generate_audio, seconds | Не читаются. У этого семейства нет параметра соотношения сторон или звуковой дорожки |
metadata | Декодируется в поля MiniMax с именами MiniMax |
Для этого семейства resolution не читается с верхнего уровня: используйте size или metadata.resolution.
Параметры провайдера (2.3)
Section titled “Параметры провайдера (2.3)”Все они передаются в metadata. Значение неверного типа JSON (например "duration": "abc") приводит к ошибке преобразования с 500 build_request_failed, а не 400; неизвестные ключи игнорируются.
| Поле | Тип | Описание |
|---|---|---|
resolution | string | 768P или 1080P; переопределяет то, что дал size |
duration | integer | 6 или 10 секунд; переопределяет duration верхнего уровня |
first_frame_image | string | Первый кадр (публичный URL или base64 data: URI), передаётся как есть |
last_frame_image | string | Последний кадр для генерации от первого к последнему, передаётся как есть |
subject_reference | array | Референс субъекта: [{"type": "character", "image": ["<url>"]}] |
prompt_optimizer | boolean | Разрешить MiniMax переписать промпт; явный false тоже передаётся |
fast_pretreatment | boolean | Флаг быстрой предобработки MiniMax, передаётся как есть |
aigc_watermark | boolean | Добавить водяной знак AIGC провайдера |
callback_url | string | Передаётся в MiniMax. RouteAPI не регистрирует и не принимает callback — опрашивайте задачу |
prompt | string | Переопределяет prompt верхнего уровня |
metadata.model перезаписывается именем upstream-модели канала, поэтому через metadata нельзя переключиться на другую (например, более дорогую) модель.
Изображение в видео (2.3)
Section titled “Изображение в видео (2.3)”curl https://api.routeapi.ai/v1/video/generations \ -H "Authorization: Bearer $ROUTEAPI_KEY" \ -H "Content-Type: application/json" \ -d '{ "model": "MiniMax-Hailuo-2.3", "prompt": "The camera slowly pushes in as the subject looks up and smiles", "duration": 6, "metadata": { "resolution": "1080P", "first_frame_image": "https://cdn.example.com/first.jpg" } }'Соответствие статусов (2.3)
Section titled “Соответствие статусов (2.3)”MiniMax v1 возвращает Preparing, Queueing, Processing, Success и Fail.
| Статус провайдера | Статус задачи | Прогресс |
|---|---|---|
Preparing, Queueing | IN_PROGRESS | 30% |
Processing | IN_PROGRESS | 50% |
Success | SUCCESS | 100% |
Fail | FAILURE | 100% |
При успехе адаптер вызывает эндпоинт получения файла MiniMax с возвращённым file_id и сохраняет полученную ссылку в result_url. Ссылка истекает по расписанию MiniMax; GET /v1/videos/{task_id}/content передаёт сохранённую ссылку через RouteAPI и требует Authorization.
Оплата (2.3)
Section titled “Оплата (2.3)”Семейство 2.3 тарифицируется по цене задачи, заданной в консоли. Отправленные разрешение и длительность на сумму не влияют, расчёта по завершении нет; неуспешная задача возвращает резерв. X-New-Api-Other-Ratios равен {}.
Ошибки (2.3)
Section titled “Ошибки (2.3)”| Статус | code | Значение |
|---|---|---|
| 400 | invalid_request | prompt отсутствует или пуст, либо некорректный JSON |
| 400 | invalid_seconds | duration / seconds отрицателен или больше 3600 |
| 400 | Числовой код MiniMax | MiniMax отклонил задачу; сообщение — его status_msg |
| 400 | task_not_exist | task_id неизвестен или принадлежит другому аккаунту |
| 500 | build_request_failed, do_request_failed | Ошибка преобразования metadata или провайдер недоступен |
| 500 | unmarshal_response_body_failed | MiniMax ответил в форме, которую адаптер не распознал |
| 502 | upstream_task_id_missing | В ответе на отправку не было ID задачи |
| статус провайдера | fail_to_fetch_task | MiniMax ответил HTTP-статусом, отличным от 200 |
Для этого семейства все бизнес-отказы MiniMax возвращаются как 400, включая ограничение частоты, — числовой code и status_msg передаются как есть, поэтому ориентируйтесь на числовой код, а не на HTTP-статус. Исключение — недостаток средств у провайдера: когда status_msg MiniMax совпадает со встроенными ключевыми словами RouteAPI о биллинге (недостаточно средств и подобные), ответ очищается до 503 get_channel_failed с общим сообщением, а сбой засчитывается как сбой канала (канал отключается автоматически, только если включено автоотключение и канал это допускает).
Сбои после отправки (модерация, таймаут провайдера) отображаются в записи задачи как FAILURE с fail_reason, и предварительно списанная сумма возвращается.