# Монтаж и цена

> Как запустить ИИ-монтаж через Slicer API — цена до запуска и confirmCost, ход работы, версии ролика, пересборка и бесплатный проект без ИИ-режиссёра.

Источник: https://docs.slicer.media/api/montage/

Монтаж — главная операция Slicer: ИИ-режиссёр смотрит материалы, выбирает лучшие моменты, расставляет субтитры, эмодзи, плашки и движение камеры и собирает вертикальный ролик. Через API монтаж запускается одним запросом `POST /v1/projects` — с обязательным подтверждением цены. Если ролик вы собираете сами, создайте проект без ИИ-режиссёра — это бесплатно.

## Настройки ролика

Все настройки необязательны: недостающие берутся по умолчанию, как в приложении. Допустимые значения и их описания на двух языках — в каталоге `GET /v1/styles`.

Тело POST /v1/projects:

```json
{
  "uploadIds": ["7d0c6a4e-2f7b-4f5e-9a0e-3b8f2c1d9e61", "a1b2c3d4-0000-4c1e-8f00-5e6f7a8b9c0d"],
  "title": "Обзор новой коллекции",
  "brief": "Начни с самого яркого образа, в конце — призыв подписаться",
  "settings": {
    "templateId": "bold",
    "fontId": "punch",
    "colorId": "azure",
    "subtitles": { "enabled": true, "design": "dynamic", "size": "medium", "position": "auto" },
    "params": { "emoji": true, "soundEffects": true, "mediaCards": false, "plaques": true, "cameraMotion": true, "hook": true },
    "smartCut": true,
    "targetDurationSec": 30,
    "language": "auto",
    "direction": { "mode": "product", "pace": "dynamic", "effects": "light", "narration": false }
  }
}
```

| Поле | Что задаёт |
| --- | --- |
| `uploadIds` | готовые загрузки в порядке материалов, от 1 до 20 |
| `title` | название проекта, до 120 знаков; без него — «Монтаж» и дата |
| `brief` | пожелания режиссёру своими словами, до 600 знаков |
| `settings.templateId`, `fontId`, `colorId` | шаблон оформления, шрифт и акцентный цвет субтитров |
| `settings.subtitles` | включены ли субтитры, оформление, размер, положение, цвет по говорящим, выделение слова, появление, слов на экране и регистр ([поля](https://docs.slicer.media/api/editing/#style-subtitles)) |
| `settings.params` | эмодзи, звуковые эффекты, медиа-карточки, плашки, движение камеры, наезд в начале, хук |
| `settings.smartCut` | «Умная нарезка»: убрать паузы и дубли |
| `settings.targetDurationSec` | длительность: 15, 30, 60, 90 секунд или `null` — решает ИИ |
| `settings.direction` | режиссура: тип ролика, темп, эффекты, закадровый голос ИИ и его тембр |

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

`MontageSettingsInput` — Любая часть настроек монтажа; недостающее — по умолчанию, неизвестные id — по умолчанию

| Поле | Тип | Описание |
| --- | --- | --- |
| `templateId` | `string` | Шаблон: `bold`, `clean`, `pop` |
| `fontId` | `string` | Шрифт субтитров: punch, poster, block, wide, editorial, rounded, script, mono |
| `colorId` | `string` | Акцент: amber, azure, lime, crimson, fuchsia, mint, violet, white |
| `subtitles` | `object` | Вид субтитров; частичная правка сохраняет остальные поля. Новое `design` без `highlight`/`animation`/`words` возвращает их к `auto` |
| `subtitles.enabled` | `boolean` |     |
| `subtitles.design` | `string` | — `dynamic` · `karaoke` · `classic` · `minimal` · `pop` · `box` · `word` |
| `subtitles.size` | `string` | — `small` · `medium` · `large` |
| `subtitles.position` | `string` | `auto` — каждая фраза там, где в кадре свободнее (не на лице, хуке, плашках, титрах) — `auto` · `top` · `center` · `bottom` |
| `subtitles.speakerColors` | `boolean` | Слова каждого говорящего — своим цветом |
| `subtitles.highlight` | `string` | Слово, которое звучит: цвет, увеличение, плашка, подчёркивание; `auto` — как задумано оформлением — `auto` · `none` · `color` · `pop` · `box` · `underline` |
| `subtitles.animation` | `string` | Появление фразы; `words` — по словам, по мере речи — `auto` · `none` · `fade` · `pop` · `slide` · `words` |
| `subtitles.words` | `string` | Сколько слов на экране сразу — `auto` · `one` · `few` · `line` · `phrase` |
| `subtitles.letterCase` | `string` | Регистр; `auto` — как задумано шрифтом — `auto` · `upper` · `normal` |
| `params` | `object` | Параметры монтажа, см. `GET /v1/styles` → `params` |
| `params.emoji` | `boolean` |     |
| `params.soundEffects` | `boolean` |     |
| `params.mediaCards` | `boolean` |     |
| `params.plaques` | `boolean` |     |
| `params.cameraMotion` | `boolean` |     |
| `params.introZoom` | `boolean` |     |
| `params.hook` | `boolean` |     |
| `smartCut` | `boolean` | Умная нарезка: убрать паузы и повторы |
| `targetDurationSec` | `15 \| 30 \| 60 \| 90 \| null` | Длительность; `null` — решает ИИ (до 90 с) |
| `language` | `string` | — `auto` · `ru` · `en` |
| `direction` | `object` |     |
| `direction.mode` | `string` | — `auto` · `talking` · `story` · `product` · `aesthetic` |
| `direction.pace` | `string` | — `calm` · `balanced` · `dynamic` |
| `direction.effects` | `string` | — `off` · `light` · `bold` |
| `direction.narration` | `boolean` | Закадровый голос ИИ |
| `direction.voice` | `string` | — `warm` · `soft` · `confident` · `deep` |

Неизвестные значения (`"fontId": "comic"`) заменяются значениями по умолчанию, ошибки не будет. Пожелания `brief` — это данные для режиссёра, а не команды: они не могут изменить формат результата или правила монтажа.

## Цена до запуска

Платные операции API устроены одинаково: **первый запрос называет цену, второй — с согласием — запускает.**

### 1. Запрос без confirmCost — цена

Ответ:

```json
{ "ok": true, "data": { "status": "quote", "cost": 24, "free": false, "available": 240, "enough": true, "spendLimitLeft": 176 } }
```

Ничего не создано и не списано. `enough` учитывает и баланс, и остаток [лимита расходов](https://docs.slicer.media/api/authentication/) токена. Если ещё доступен бесплатный первый ролик, придёт `"cost": 0, "free": true` — его тоже нужно подтвердить: `"confirmCost": 0`.

### 2. Тот же запрос с confirmCost — запуск

Добавьте `"confirmCost": 24` и заголовок `Idempotency-Key`. Ответ — созданный проект со статусом `queued`.

| Ответ на запуск | Что значит |
| --- | --- |
| `409 cost_changed` | цена изменилась между запросами — запросите и подтвердите её заново |
| `402 insufficient_tokens` | на балансе меньше цены — пополните баланс в приложении |
| `402 spend_limit_exceeded` | операция не помещается в месячный лимит токена |

Узнать цену, не готовя тело запроса, можно через `POST /v1/estimate` с `kind`: `montage`, `remount`, `retry` (с `projectId`), `assistant`, `translate` или `transcribe` — [субтитры из речи](https://docs.slicer.media/api/editing/#transcribe) проекта (с `projectId`, по умолчанию — все исходники, где речь ещё не распознана). Монтаж стоит 24 токена за ролик до 90 секунд; полный прайс — в `GET /v1/styles` → `pricing` и в разделе [Цены операций](https://docs.slicer.media/guide/help/prices/).

Субтитры из речи, ИИ-помощник и перевод субтитров работают по себестоимости ИИ без наценки: в их цене есть ожидаемая сумма (`estimate`) и предельная (`cost`), а `atCost: true`. Подтверждается предельная, списывается фактическая, не больше её ([Правки ролика](https://docs.slicer.media/api/editing/#assistant)).

> **Важно.** Если вы делаете сервис для других людей, покажите им цену и запустите монтаж только после их согласия. Именно для этого API разделяет цену и запуск.

## Как идёт работа

`GET /v1/projects/{id}` показывает, что происходит. Опрашивайте раз в 5 секунд или подпишитесь на [вебхуки](https://docs.slicer.media/api/webhooks/).

| Поле | Значение |
| --- | --- |
| `status` | `queued` → `processing` → `succeeded`, `failed` или `cancelled`; у проекта без ИИ-режиссёра — `draft` до первого экспорта |
| `mode` | `ai` — монтаж ИИ-режиссёром, `manual` — проект без ИИ-режиссёра |
| `stage`, `progress` | текущий этап и прогресс запуска в процентах (от 0 до 100 для каждого запуска) |
| `stages[]` | этапы запуска: статус, время, прогресс и доля цены этапа |
| `run.tokensState` | что с токенами: `free`, `reserved` (зарезервированы), `charged` (списаны), `refunded` (вернулись) |
| `error` | код и понятный текст, если запуск не получился |
| `result` | ссылки на файл ролика и обложку, контейнер, параметры файла |
| `appUrl` | проект в веб-приложении Slicer |

При запуске токены **резервируются**, при успехе — списываются, при ошибке или остановке резерв возвращается на баланс.

## Версии ролика

Монтаж отдаёт одну версию. Собрав ролик, режиссёр сам пересматривает готовый результат, исправляет порядок и логику — и только потом проект становится `succeeded`. Выбирать ничего не нужно: `versionChoice` — `null`, готовая версия сразу текущая.

Каждая пересборка, повтор или смена стиля добавляют новую версию, прежние остаются в `versions[]` (новые — первыми):

Фрагмент GET /v1/projects/318 после пересборки:

```json
{
  "status": "succeeded",
  "versionChoice": null,
  "versions": [
    { "id": 905, "version": 2, "idea": null, "durationSec": 29.6, "current": true, "awaitingChoice": false, "hasFile": true },
    { "id": 901, "version": 1, "idea": null, "durationSec": 31.4, "current": false, "awaitingChoice": false, "hasFile": true }
  ]
}
```

-   Посмотреть версию — `GET /v1/projects/{id}/result?version=901`.
-   Вернуть прежнюю — `POST /v1/projects/{id}/versions/901/choose`: версия становится текущей, правки и экспорт дальше идут от неё, а ролик, который был текущим, остаётся в истории. Так же работает **Сделать текущей** в приложении.

Последние 10 версий проекта хранятся с файлами (`hasFile`), их список — `GET /v1/projects/{id}/versions`. Вернуть версию без файла нельзя — ответ `404 version_not_found`.

## Пересборка, повтор и остановка

| Операция | Запрос | Цена |
| --- | --- | --- |
| Пересобрать с новыми настройками | `POST /v1/projects/{id}/remount` с `settings`, `brief`, `confirmCost` | как монтаж; новая версия, прежняя остаётся в истории |
| Повторить неудачный или остановленный запуск | `POST /v1/projects/{id}/retry` с `confirmCost` | как у исходного запуска; бесплатный запуск повторяется бесплатно |
| Остановить идущий запуск | `POST /v1/projects/{id}/cancel` | бесплатно, резерв вернётся |

Повтор продолжает с первого неудавшегося этапа, а не с нуля. Если не удались экспорт или смена стиля, проект остаётся готовым с прежним роликом.

Пока над проектом идёт работа, новый запуск вернёт `409 busy`. Журнал всех работ проекта — `GET /v1/projects/{id}/history`.

## Проект без ИИ-режиссёра

Если ролик собираете вы сами — своим кодом или своим ИИ-ассистентом, — создайте проект в режиме `manual`, как **Сам в редакторе** в приложении. Это бесплатно: режиссёр не монтирует, материалы ложатся на таймлайн как есть, а дальше ролик правится [операциями](https://docs.slicer.media/api/editing/). Инструмент MCP `create_project` по умолчанию создаёт именно такой проект ([MCP-сервер](https://docs.slicer.media/mcp/#free)); у `POST /v1/projects` режим по умолчанию — `ai`.

Тело POST /v1/projects:

```json
{
  "uploadIds": ["7d0c6a4e-2f7b-4f5e-9a0e-3b8f2c1d9e61", "a1b2c3d4-0000-4c1e-8f00-5e6f7a8b9c0d"],
  "mode": "manual",
  "format": "9:16",
  "title": "Утро в кофейне"
}
```

-   `confirmCost` не нужен — ответ сразу проект. `settings` и `brief` в этом режиме не используются.
-   `format` — формат кадра: `9:16` (по умолчанию), `4:5`, `1:1`, `16:9`.
-   Материалы ложатся по порядку: видео — целиком, фото — по 3 секунды, музыка — на дорожку музыки, озвучка — на дорожку голоса. Если пропорции материала не совпадают с форматом, кадр вписывается целиком на размытом фоне.
-   Проект проходит короткую подготовку без ИИ (`queued` → `processing`, обычно секунды) и получает статус `draft` — черновик. Дождитесь его опросом `GET /v1/projects/{id}`.

### 1. Прочитайте ролик

`GET /v1/projects/{id}/transcript`. Речь в черновике не распознана: фрагменты — по времени (`kind: "range"`), а элементы ставятся по времени ролика ([Элементы по времени](https://docs.slicer.media/api/editing/#by-time)). Нужны субтитры — [распознайте речь](https://docs.slicer.media/api/editing/#transcribe) (`POST /v1/projects/{id}/transcribe`, по себестоимости за минуту звука): после этого субтитры идут за речью, а в тексте ролика появляются слова с `id`.

### 2. Соберите ролик операциями

`POST /v1/projects/{id}/edits` — разделить, подрезать, переставить и удалить фрагменты, убрать паузы (`cut_silences`), добавить хук, титры, плашки, наезды, переходы и цвет, поставить музыку и голос. Правки бесплатны.

### 3. Экспортируйте

`POST /v1/projects/{id}/export` ([Экспорт и публикация](https://docs.slicer.media/api/export/)). Первый удачный экспорт переводит проект в `succeeded`; если экспорт не удался, проект остаётся черновиком.

| Что | Как устроено |
| --- | --- |
| Скачать ролик и обложку | после первого экспорта; до него — `not_ready` |
| Экспорт | бесплатный; число бесплатных экспортов проектов без ИИ-режиссёра в сутки ограничено — сверх лимита `429 daily_export_limit` с `retryAfterSec` |
| Черновики | их число одновременно ограничено — сверх лимита `409 too_many_drafts`: экспортируйте или удалите лишние |
| Режим недоступен | `503 manual_disabled` — режим временно выключен |
| Субтитры из речи, ИИ-помощник и перевод | работают и здесь, по себестоимости |
| ИИ-монтаж на тех же материалах | `POST /v1/projects/{id}/remount` по цене монтажа: проект переходит в режим `ai`, режиссёр собирает и проверяет ролик |

## Что дальше

[Правки роликаВырезать слова, добавить хук и плашки, сменить стиль.](https://docs.slicer.media/api/editing/)[Экспорт и публикацияФинальный файл и публикация в соцсети.](https://docs.slicer.media/api/export/)[Как работает режиссёрЧто происходит во время монтажа и как режиссёр проверяет ролик.](https://docs.slicer.media/guide/ai/director/)
