{
  "openapi": "3.1.0",
  "info": {
    "title": "Syllaby API",
    "version": "2.0.0",
    "description": "The Syllaby API lets you build Syllaby’s content-generation capabilities\ninto your own apps and workflows. This **v2** release covers **faceless\nvideos** and the resources around them — scripts, presets, assets, and\naccount credits. More capabilities will be added over time.\n\n## Typical flow (faceless video)\n**Standard flow (AI-generated or stock visuals):**\n1. **Create** a draft video — `POST /faceless`.\n2. **Add a script** — generate one with `PUT /faceless/{faceless}/scripts`, or supply your own.\n3. **Configure** voice, genre, captions, and visuals — `PATCH /faceless/{faceless}`. Browse the available options at `GET /faceless/options`.\n4. *(Optional)* **Estimate** the credit cost — `GET /faceless/{faceless}/estimate`.\n5. **Render** — `POST /faceless/{faceless}/render` (returns `202`).\n6. **Track progress** — poll `GET /faceless/{id}` and read `data.video.status` (`rendering` → `completed`/`failed`); the `video` object is always embedded. On failure, retry with `POST /faceless/{faceless}/retry`. See **Get your rendered video** below.\n7. *(Optional)* **Export** a restyled cut — `POST /faceless/{faceless}/export`.\n\n**URL-based flow (build a video from a product/web page):**\n`create (type=url-based)` → `scrape-images` *(free)* → `scrape-script` *(charges `CONTENT_PROMPT_REQUESTED`, same as `PUT /scripts`)* → configure → render *(charges)* → poll.\n\n## Build from a URL\nThe `url-based` type lets you build a faceless video from the content of any publicly reachable web page (product listing, blog post, landing page) — Syllaby extracts images and can generate a matching script directly from the page.\n\n**Steps:**\n1. **Create** — `POST /faceless` with `type: \"url-based\"`. The `type` is fixed at creation and cannot be changed later.\n2. **Scrape images** — `POST /faceless/{faceless}/scrape-images` with `{ \"url\": \"https://…\" }`. **Free** — no credits charged. Extracts product/page images and attaches them to the video as ordered assets.\n3. **Scrape script** — `POST /faceless/{faceless}/scrape-script` with the page URL plus generation options (`duration`, `style`, `tone`, `language`). **💳 Charges `CONTENT_PROMPT_REQUESTED` credits** (the same amount as `PUT /faceless/{faceless}/scripts`). Generates and stores a narration script written from the page content. You may skip this step and supply your own script via `PATCH /faceless/{faceless}` instead.\n4. **Configure** — `PATCH /faceless/{faceless}` (voice, captions, transitions, etc.).\n5. **Render** — `POST /faceless/{faceless}/render`. **💳 Charges render credits.** Requires that scrape-images has run at least once (otherwise returns `422 assets`). The scraped images become the visual slides.\n6. **Poll** — `GET /faceless/{id}` until `data.video.status` is `completed`.\n\n> **Social and unsupported URLs are rejected.** URLs pointing to social-media platforms (YouTube, TikTok, Twitter/X, Instagram, Facebook, etc.) and any un-parseable or unreachable page return `422` on both scrape endpoints.\n\n## Get your rendered video\nRendering is asynchronous — the render call returns before the file exists. From request to playable file:\n\n1. **Create** the faceless video — `POST /faceless`. Note the `id` field in the response.\n2. *(Optional)* **Generate a script** — `PUT /faceless/{faceless}/scripts`.\n3. **Render** — `POST /faceless/{faceless}/render`. Returns `202` immediately; `meta.credits` reports the charge.\n4. **Poll** — `GET /faceless/{id}` on a sensible cadence (every 5–10 seconds is plenty). Every response embeds the render state under `data.video` — no `include` parameter needed.\n5. **Done** — when `data.video.status` is `completed`, the playable file is at `data.video.url`. If it is `failed`, the reason is in `data.video.failure` (`code` and `message`); fix what you can and retry with `POST /faceless/{faceless}/retry`.\n\n> **Important — poll with the right identifier.** Use the faceless **`id`** from the create/render response, **not** `video_id`. They are different identifiers: `id` is the faceless video, `video_id` is its underlying video record. Calling `GET /faceless/{video_id}` returns `404`.\n\n## Before you render — checklist\nRendering charges credits and has a few preconditions. The render call validates them **before** anything is charged, so a missed step fails fast with a `402`/`403` (or `422`) and costs nothing. Before calling `POST /faceless/{faceless}/render`:\n\n1. **Script set** — generate one with `PUT /faceless/{faceless}/scripts`, or supply your own via `PATCH /faceless/{faceless}`. Missing → **`403` `A script is required before rendering.`**\n2. **Voice chosen** — set `voice_id` via `PATCH /faceless/{faceless}`. Missing → **`403` `Voice was not provided.`** (or `Voice not found.` for an unknown id).\n3. **Options configured** — genre, captions, and visuals. Genre is **required** for `ai-visuals` / `ai-clips`; missing it → **`422` `A genre is required for AI visuals and AI clips.`** Browse valid ids/slugs at `GET /faceless/options`.\n4. **Credits sufficient** — check the cost against your balance with `GET /faceless/{faceless}/estimate`. Too few → **`402` `INSUFFICIENT-CREDITS`** with `required` and `available` in the error body.\n5. **For `url-based` videos** — run `POST /faceless/{faceless}/scrape-images` at least once before rendering. A url-based render with no scraped assets → **`422` `assets`** (the images become the visual slides; without them the render would produce an empty video).\n\nThe video must also not be **busy** (already rendering or syncing) → **`403` `The video is processing currently. Please try again once finished`**. See each endpoint's *Preconditions & common errors* for the full list.\n\n## Authentication\nAll endpoints require a **Bearer token**. Send it on every request:\n\n```http\nAuthorization: Bearer <your-api-token>\n```\n\nGenerate a token from your Syllaby account settings. Treat it like a\npassword — never expose it in client-side code.\n\nThe v2 API is token-only and stateless: authenticate with `Authorization: Bearer <token>` on every request. Do **not** send cookies or a CSRF token — they are ignored.\n\n## Base URL\nProduction requests go to `https://api.syllaby.io/v2`. Every path in this\nreference is relative to that base.\n\n## Subscription required\nAll faceless-video and preset endpoints require an **active\nsubscription** — reads included. Without one, every request to that surface\nis rejected with `403 SUBSCRIPTION-REQUIRED` (`An active subscription is\nrequired.`) before any ownership, credit, or validation check. The public\nAPI has no free tier. Only `GET /me`, `GET /credits/costs`, and\n`GET /credits/history` are reachable without an active subscription.\n\n## Credits\nGenerative actions (rendering, script generation) consume account credits.\nUse the credit-cost and estimate endpoints to check the price before you\nspend, and the credit history endpoint to audit usage.\nCredits consumed through the public API are tagged at the ledger level, so\nAPI-originated spend is distinguishable from in-app usage. Audit it with\n`GET /credits/history` — each entry records the action and the credits charged —\nand look up the per-action price list with `GET /credits/costs`.\n\n## Responses & errors\nResponses are JSON wrapped in a `{ message, status, data }` envelope.\nErrors use standard HTTP status codes — `400` (bad request, e.g. an\n`include` value outside the endpoint's allowlist), `401` (unauthenticated),\n`402` (payment required — insufficient credits), `404` (not found),\n`422` (validation), and `429` (rate limited).\n\n## Rate limiting\nRequests are rate limited **per API token** — 30 requests per minute by\ndefault. Every response carries `X-RateLimit-Limit` and\n`X-RateLimit-Remaining` headers so you can pace requests proactively.\nWhen you exceed the limit the API responds with `429 Too Many Requests`\nplus `Retry-After` (seconds to wait) and `X-RateLimit-Reset` (Unix\ntimestamp when the window resets) — back off until then and retry."
  },
  "servers": [
    {
      "url": "https://api.syllaby.io/v2",
      "description": "Production"
    },
    {
      "url": "https://api.syllaby-stg.com/v2",
      "description": "Staging"
    }
  ],
  "security": [
    {
      "http": []
    }
  ],
  "paths": {
    "/me": {
      "get": {
        "operationId": "getMyAccount",
        "summary": "Get current account",
        "tags": [
          "Account"
        ],
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/MeResource"
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "id": 1,
                    "name": "Jane Doe",
                    "email": "jane@example.com",
                    "email_verified": true,
                    "credits": {
                      "remaining": 120,
                      "total": 150,
                      "extra": 0
                    },
                    "subscription": {
                      "exists": true,
                      "active": true,
                      "trial": false,
                      "plan": "Pro",
                      "ends_at": "2026-02-01T00:00:00+00:00"
                    },
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns the authenticated user's public account profile: identity, credit balance, and a high-level subscription summary (no billing-provider internals)."
      }
    },
    "/credits/costs": {
      "get": {
        "operationId": "listCreditCosts",
        "summary": "List credit costs",
        "tags": [
          "Account"
        ],
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "type": "object",
                      "description": "Map of feature key to its credit cost. Each value is an object with a `credits` count and an optional `free` allowance.",
                      "additionalProperties": {
                        "type": "object",
                        "properties": {
                          "credits": {
                            "type": "integer",
                            "description": "Credits charged per use of the feature."
                          },
                          "free": {
                            "type": "integer",
                            "description": "Number of free uses granted before credits are charged, if any."
                          }
                        }
                      }
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "idea_discovery": {
                      "credits": 15
                    },
                    "avatar": {
                      "credits": 30
                    },
                    "faceless": {
                      "credits": 13
                    },
                    "image_regenerations": {
                      "credits": 1,
                      "free": 3
                    },
                    "thumbnail_generation": {
                      "credits": 3
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns the per-feature credit cost map so you can show users what each action will cost before they spend credits."
      }
    },
    "/credits/history": {
      "get": {
        "operationId": "listCreditHistory",
        "summary": "List credit history",
        "tags": [
          "Account"
        ],
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "": {
                      "description": "The  value for the resource."
                    }
                  },
                  "required": [
                    "status",
                    "message",
                    null
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": [
                    {
                      "label": "Faceless video",
                      "content_type": "Faceless video generated",
                      "credit_spend": "-30",
                      "transaction_type": "Debit",
                      "created_at": "2026-01-01T12:00:00.000000Z"
                    }
                  ],
                  "meta": {
                    "current_page": 1,
                    "per_page": 15,
                    "total": 1
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "Returns the authenticated user's credit ledger (debits and credits), newest first by default. Pass `order=ASC` to reverse, and `per_page` to set the page size (default 12, max 50).",
        "parameters": [
          {
            "name": "order",
            "in": "query",
            "required": false,
            "description": "Sort direction by date. `DESC` (newest first, default) or `ASC`.",
            "schema": {
              "type": "string",
              "enum": [
                "ASC",
                "DESC"
              ],
              "default": "DESC"
            },
            "example": "DESC"
          },
          {
            "name": "per_page",
            "in": "query",
            "required": false,
            "description": "Number of entries per page. Defaults to 12; capped at 50.",
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 50,
              "default": 12
            },
            "example": 12
          }
        ]
      }
    },
    "/faceless/options": {
      "get": {
        "operationId": "listFacelessOptions",
        "description": "**Reference data** — the slugs/ids for Step 3 (Configure).\n\nReturns all reference data for building a faceless video in one payload, split into two layers. `mandatory` holds the inputs a typical render needs — aspect_ratios, genres, image_engines, voices. `optional` holds the styling and advanced groups — fonts, transitions, backgrounds, caption effects and positions, overlays, watermark positions, animations, sound effects, volumes, clip engines, and characters. Use the returned slugs/ids when creating, updating, or rendering a video.",
        "summary": "List faceless options",
        "tags": [
          "Faceless Videos"
        ],
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "type": "object",
                      "description": "Available option groups, split into the ones a render needs and the rest.",
                      "properties": {
                        "mandatory": {
                          "type": "object",
                          "description": "Option groups a typical render needs — pick from these.",
                          "properties": {
                            "aspect_ratios": {
                              "type": "array",
                              "description": "Output frame ratios a render can target.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "slug": {
                                    "type": "string",
                                    "description": "Aspect-ratio value to send (e.g. \"9:16\")."
                                  },
                                  "label": {
                                    "type": "string",
                                    "description": "Human-readable orientation label (e.g. \"Portrait\")."
                                  }
                                }
                              }
                            },
                            "genres": {
                              "type": "array",
                              "description": "Visual genres/styles that drive the image-prompt look.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "id": {
                                    "type": "integer",
                                    "description": "Identifier of the genre to send as `genre_id`."
                                  },
                                  "name": {
                                    "type": "string",
                                    "description": "Display name of the genre."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable slug for the genre."
                                  }
                                }
                              }
                            },
                            "image_engines": {
                              "type": "array",
                              "description": "Text-to-image engines available for image-based renders.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "id": {
                                    "type": "integer",
                                    "description": "Identifier of the engine to send as `image_engine_id`."
                                  },
                                  "name": {
                                    "type": "string",
                                    "description": "Display name of the engine."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable slug for the engine."
                                  },
                                  "type": {
                                    "type": "string",
                                    "description": "Engine category (e.g. \"text-to-image\")."
                                  },
                                  "cost": {
                                    "type": "integer",
                                    "description": "Credit cost multiplier applied when this engine is used."
                                  }
                                }
                              }
                            },
                            "voices": {
                              "type": "array",
                              "description": "Narration voices available for the video.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "id": {
                                    "type": "integer",
                                    "description": "Identifier of the voice to send as `voice_id`."
                                  },
                                  "name": {
                                    "type": "string",
                                    "description": "Display name of the voice."
                                  },
                                  "language": {
                                    "type": "string",
                                    "description": "Spoken language of the voice."
                                  },
                                  "gender": {
                                    "type": "string",
                                    "description": "Voice gender."
                                  }
                                }
                              }
                            }
                          }
                        },
                        "optional": {
                          "type": "object",
                          "description": "Styling and advanced option groups — all optional.",
                          "properties": {
                            "fonts": {
                              "type": "array",
                              "description": "Caption font families.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "name": {
                                    "type": "string",
                                    "description": "Human-readable label for the option."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable identifier to send back when configuring a render."
                                  }
                                }
                              }
                            },
                            "transitions": {
                              "type": "array",
                              "description": "Transitions applied between scenes.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "name": {
                                    "type": "string",
                                    "description": "Human-readable label for the option."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable identifier to send back when configuring a render."
                                  }
                                }
                              }
                            },
                            "backgrounds": {
                              "type": "array",
                              "description": "Background assets that can sit behind the video.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "id": {
                                    "type": "integer",
                                    "description": "Identifier of the background to send as `background_id`."
                                  },
                                  "name": {
                                    "type": "string",
                                    "description": "Display name of the background."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable slug for the background."
                                  }
                                }
                              }
                            },
                            "caption_effects": {
                              "type": "array",
                              "description": "Visual effects applied to on-screen captions.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "name": {
                                    "type": "string",
                                    "description": "Human-readable label for the option."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable identifier to send back when configuring a render."
                                  }
                                }
                              }
                            },
                            "caption_positions": {
                              "type": "array",
                              "description": "On-screen placements for captions.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "name": {
                                    "type": "string",
                                    "description": "Human-readable label for the option."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable identifier to send back when configuring a render."
                                  }
                                }
                              }
                            },
                            "overlays": {
                              "type": "array",
                              "description": "Overlay styles applied over the video.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "name": {
                                    "type": "string",
                                    "description": "Human-readable label for the option."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable identifier to send back when configuring a render."
                                  }
                                }
                              }
                            },
                            "watermark_positions": {
                              "type": "array",
                              "description": "Placements available for a watermark.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "name": {
                                    "type": "string",
                                    "description": "Human-readable label for the option."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable identifier to send back when configuring a render."
                                  }
                                }
                              }
                            },
                            "animations": {
                              "type": "array",
                              "description": "Image animation styles (e.g. pan/zoom).",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "name": {
                                    "type": "string",
                                    "description": "Human-readable label for the option."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable identifier to send back when configuring a render."
                                  }
                                }
                              }
                            },
                            "sfx": {
                              "type": "array",
                              "description": "Sound-effect tracks that can be layered onto the video.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "name": {
                                    "type": "string",
                                    "description": "Human-readable label for the option."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable identifier to send back when configuring a render."
                                  }
                                }
                              }
                            },
                            "volumes": {
                              "type": "array",
                              "description": "Background-music volume levels.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "name": {
                                    "type": "string",
                                    "description": "Human-readable label for the option."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable identifier to send back when configuring a render."
                                  }
                                }
                              }
                            },
                            "clip_engines": {
                              "type": "array",
                              "description": "Text-to-video (clip) engines available for clip-based renders.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "id": {
                                    "type": "integer",
                                    "description": "Identifier of the engine to send as `clip_engine_id`."
                                  },
                                  "name": {
                                    "type": "string",
                                    "description": "Display name of the engine."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable slug for the engine."
                                  },
                                  "type": {
                                    "type": "string",
                                    "description": "Engine category (e.g. \"text-to-video\")."
                                  },
                                  "cost": {
                                    "type": "integer",
                                    "description": "Credit cost multiplier applied when this engine is used."
                                  }
                                }
                              }
                            },
                            "characters": {
                              "type": "array",
                              "description": "Consistent AI characters you can cast in the video.",
                              "items": {
                                "type": "object",
                                "properties": {
                                  "id": {
                                    "type": "integer",
                                    "description": "Numeric identifier of the character."
                                  },
                                  "uuid": {
                                    "type": "string",
                                    "description": "Stable UUID of the character to send as `character_id`."
                                  },
                                  "name": {
                                    "type": "string",
                                    "description": "Display name of the character."
                                  },
                                  "slug": {
                                    "type": "string",
                                    "description": "Stable slug for the character."
                                  },
                                  "gender": {
                                    "type": "string",
                                    "description": "Character gender."
                                  },
                                  "status": {
                                    "type": "string",
                                    "description": "Readiness state of the character (e.g. \"ready\")."
                                  }
                                }
                              }
                            }
                          }
                        }
                      }
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "mandatory": {
                      "aspect_ratios": [
                        {
                          "slug": "9:16",
                          "label": "Portrait"
                        }
                      ],
                      "genres": [
                        {
                          "id": 3,
                          "name": "Cinematic",
                          "slug": "cinematic"
                        }
                      ],
                      "image_engines": [
                        {
                          "id": 5,
                          "name": "Hyperflux",
                          "slug": "hyperflux",
                          "type": "text-to-image",
                          "cost": 2
                        }
                      ],
                      "voices": [
                        {
                          "id": 12,
                          "name": "Aria",
                          "language": "english",
                          "gender": "female"
                        }
                      ]
                    },
                    "optional": {
                      "fonts": [
                        {
                          "name": "Inter",
                          "slug": "inter"
                        }
                      ],
                      "transitions": [
                        {
                          "name": "Fade",
                          "slug": "fade"
                        }
                      ],
                      "backgrounds": [
                        {
                          "id": 7,
                          "name": "Studio",
                          "slug": "studio"
                        }
                      ],
                      "caption_effects": [
                        {
                          "name": "None",
                          "slug": "none"
                        }
                      ],
                      "caption_positions": [
                        {
                          "name": "Center",
                          "slug": "center"
                        }
                      ],
                      "overlays": [
                        {
                          "name": "None",
                          "slug": "none"
                        }
                      ],
                      "watermark_positions": [
                        {
                          "name": "Bottom Right",
                          "slug": "bottom-right"
                        }
                      ],
                      "animations": [
                        {
                          "name": "Pan In (Zoom In)",
                          "slug": "pan-in"
                        }
                      ],
                      "sfx": [
                        {
                          "name": "None",
                          "slug": "none"
                        }
                      ],
                      "volumes": [
                        {
                          "name": "Medium",
                          "slug": "medium"
                        }
                      ],
                      "clip_engines": [
                        {
                          "id": 9,
                          "name": "Nano Banana",
                          "slug": "nano-banana",
                          "type": "text-to-video",
                          "cost": 4
                        }
                      ],
                      "characters": [
                        {
                          "id": 2,
                          "uuid": "chr_123",
                          "name": "Maya",
                          "slug": "maya",
                          "gender": "female",
                          "status": "ready"
                        }
                      ]
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequired"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        }
      }
    },
    "/faceless": {
      "post": {
        "operationId": "createFacelessVideo",
        "summary": "Create a faceless video",
        "tags": [
          "Faceless Videos"
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/CreateFacelessRequest"
              },
              "example": {
                "title": "My first faceless video",
                "type": "ai-visuals"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 201,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessResource"
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 201,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "video_id": 10,
                    "voice_id": 12,
                    "music_id": null,
                    "background_id": null,
                    "estimated_duration": 60,
                    "type": "faceless",
                    "genre": {
                      "id": 3,
                      "name": "Cinematic",
                      "slug": "cinematic",
                      "active": true
                    },
                    "script": "Three habits that quietly improve your focus.",
                    "hash": "abc123",
                    "options": {
                      "aspect_ratio": "9:16"
                    },
                    "is_transcribed": false,
                    "watermark_id": null,
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z",
                    "video": {
                      "id": 10,
                      "user_id": 1,
                      "idea_id": null,
                      "scheduler_id": null,
                      "title": "Focus habits",
                      "type": "faceless",
                      "url": null,
                      "status": "draft",
                      "retries": 0,
                      "hash": "abc123",
                      "synced_at": null,
                      "metadata": {
                        "ai_labels": true,
                        "custom_description": null
                      },
                      "failure": null,
                      "created_at": "2026-01-01T12:00:00.000000Z",
                      "updated_at": "2026-01-01T12:00:00.000000Z"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "422": {
            "$ref": "#/components/responses/ValidationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "**Step 1 of 7 · Create.**\n\nCreates a new faceless video in draft state. Returns the created video — with its render state embedded under `data.video` — so you can configure it (script, voice, visuals) and then render it. This does not start rendering.\n\n**Required:** `title` and `type` — name the video and choose how its visuals are sourced (`type` is fixed at creation and cannot be changed later).\n\nKeep the returned **`id`**: it is the identifier for every follow-up call, including polling `GET /faceless/{id}` (do not use `video_id` for that).\n\n**Requires an active subscription** — no active subscription → `403` `SUBSCRIPTION-REQUIRED` `An active subscription is required.`; the public API has no free tier, so subscribe before creating a video.\n\n→ **Next:** Step 2 — add a script with `PUT /faceless/{faceless}/scripts` (or supply your own via `PATCH /faceless/{faceless}`)."
      }
    },
    "/faceless/{faceless}/scripts": {
      "put": {
        "operationId": "generateFacelessScript",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/GenerateFacelessScriptRequest"
              },
              "example": {
                "topic": "Morning routines for better focus",
                "tone": "professional",
                "style": "educational",
                "language": "english",
                "duration": 60
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessResource"
                    },
                    "meta": {
                      "type": "object",
                      "description": "Present on credit-charging endpoints.",
                      "properties": {
                        "credits": {
                          "type": "object",
                          "description": "Credit accounting for this operation.",
                          "properties": {
                            "cost": {
                              "type": "integer",
                              "description": "The exact credits charged for generating the script."
                            },
                            "remaining": {
                              "type": "integer",
                              "description": "Your credit balance after the charge."
                            }
                          }
                        }
                      }
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "video_id": 10,
                    "voice_id": 12,
                    "music_id": null,
                    "background_id": null,
                    "estimated_duration": 60,
                    "type": "faceless",
                    "genre": {
                      "id": 3,
                      "name": "Cinematic",
                      "slug": "cinematic",
                      "active": true
                    },
                    "script": "Three habits that quietly improve your focus.",
                    "hash": "abc123",
                    "options": {
                      "aspect_ratio": "9:16"
                    },
                    "is_transcribed": false,
                    "watermark_id": null,
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z",
                    "video": {
                      "id": 10,
                      "user_id": 1,
                      "idea_id": null,
                      "scheduler_id": null,
                      "title": "Focus habits",
                      "type": "faceless",
                      "url": null,
                      "status": "draft",
                      "retries": 0,
                      "hash": "abc123",
                      "synced_at": null,
                      "metadata": {
                        "ai_labels": true,
                        "custom_description": null
                      },
                      "failure": null,
                      "created_at": "2026-01-01T12:00:00.000000Z",
                      "updated_at": "2026-01-01T12:00:00.000000Z"
                    }
                  },
                  "meta": {
                    "credits": {
                      "cost": 5,
                      "remaining": 875
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "402": {
            "$ref": "#/components/responses/PaymentRequired"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "422": {
            "$ref": "#/components/responses/ValidationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "500": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "anyOf": [
                        {
                          "type": "string"
                        },
                        {
                          "type": "array",
                          "items": {}
                        },
                        {
                          "type": "null"
                        }
                      ]
                    },
                    "error": {
                      "type": "object",
                      "properties": {
                        "code": {
                          "type": "null"
                        },
                        "status": {
                          "type": "integer",
                          "const": 500
                        },
                        "": {
                          "type": "string"
                        }
                      },
                      "required": [
                        "code",
                        "status",
                        null
                      ]
                    }
                  },
                  "required": [
                    "message",
                    "error"
                  ]
                }
              }
            }
          }
        },
        "summary": "Generate a faceless script",
        "x-badges": [
          {
            "name": "Charges credits"
          }
        ],
        "description": "**Step 2 of 7 · Add a script.** *(Alternative: skip this generated-script step and supply a full custom script verbatim via `PATCH /faceless/{faceless}` — set the `script` field.)*\n\n💳 Charges credits. The response `meta.credits` shows the cost and your remaining balance.\n\n**Before you can generate a script:** create a faceless video first (`POST /faceless`). This charges credits, so make sure your balance is sufficient — `meta.credits.cost` is the exact amount charged.\n\nGenerates a narration script for the faceless video from a topic, tone, style, language, and target duration, and stores it on the video.\n\n**Note the method:** this endpoint is a `PUT` (idempotent replace of the video's script), not a `POST` — each call regenerates the script and overwrites the previous one.\n\n**Preconditions & common errors:**\n- **No active subscription** → `403` `SUBSCRIPTION-REQUIRED` `An active subscription is required.` — checked before anything else; the public API has no free tier.\n- **Video busy** (rendering or syncing) → `403` — you cannot regenerate the script while the video is processing.\n- **Not your video** → `403`.\n- **Insufficient credits** → `402` with code `INSUFFICIENT-CREDITS` and `required` / `available` in the error body.\n- **Missing required fields** (`topic`, `tone`, `style`, `language`, `duration`) → `422`; `topic` is capped at 500 characters.\n\n→ **Next:** Step 3 — configure voice, genre, captions, and visuals with `PATCH /faceless/{faceless}`."
      }
    },
    "/faceless/{faceless}/scrape-images": {
      "post": {
        "operationId": "scrapeFacelessImages",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "requestBody": {
          "description": "The URL to extract images from.",
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "url"
                ],
                "properties": {
                  "url": {
                    "type": "string",
                    "format": "uri",
                    "description": "Publicly reachable web page URL to extract product/page images from. Social-media URLs (YouTube, TikTok, Twitter/X, Instagram, Facebook, etc.) are rejected with `422`.",
                    "example": "https://www.amazon.com/dp/B0CXYZ1234"
                  }
                }
              },
              "example": {
                "url": "https://www.amazon.com/dp/B0CXYZ1234"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessResource"
                    },
                    "meta": {
                      "type": "string",
                      "description": "Pagination and listing metadata."
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data",
                    "meta"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "video_id": 10,
                    "voice_id": 12,
                    "music_id": null,
                    "background_id": null,
                    "estimated_duration": 60,
                    "type": "url-based",
                    "genre": {
                      "id": 3,
                      "name": "Cinematic",
                      "slug": "cinematic",
                      "active": true
                    },
                    "script": "Three habits that quietly improve your focus.",
                    "hash": "abc123",
                    "options": {
                      "aspect_ratio": "9:16"
                    },
                    "is_transcribed": false,
                    "watermark_id": null,
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z",
                    "assets": [
                      {
                        "id": 1,
                        "user_id": 1,
                        "type": "faceless_background",
                        "status": "success",
                        "order": 0,
                        "media": [
                          {
                            "id": 5,
                            "name": "scene-1",
                            "file_name": "scene-1.png",
                            "mime_type": "image/png",
                            "extension": "png",
                            "download_url": "https://cdn.syllaby.dev/assets/scene-1.png"
                          }
                        ],
                        "created_at": "2026-01-01T12:00:00.000000Z",
                        "updated_at": "2026-01-01T12:00:00.000000Z"
                      }
                    ],
                    "video": {
                      "id": 10,
                      "user_id": 1,
                      "idea_id": null,
                      "scheduler_id": null,
                      "title": "Focus habits",
                      "type": "faceless",
                      "url": null,
                      "status": "draft",
                      "retries": 0,
                      "hash": "abc123",
                      "synced_at": null,
                      "metadata": {
                        "ai_labels": true,
                        "custom_description": null
                      },
                      "failure": null,
                      "created_at": "2026-01-01T12:00:00.000000Z",
                      "updated_at": "2026-01-01T12:00:00.000000Z"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "422": {
            "$ref": "#/components/responses/ValidationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "summary": "Scrape images from a URL",
        "description": "**URL-based flow · Step A · Scrape images** *(free)* — extract images from a web page and attach them to a `url-based` video. Required before rendering.\n\n**Free — no credits charged.** Extracts images from the supplied web page URL and attaches them to the `url-based` faceless video as ordered assets. A subsequent `GET /faceless/{faceless}/assets` will list them.\n\n**This endpoint is only valid for `url-based` videos.** Calling it on any other type returns `422`.\n\n**Before you can render a `url-based` video:** you must call this endpoint at least once. A render attempted without scraped assets returns `422 assets`.\n\n**Preconditions & common errors:**\n- **Not a `url-based` video** → `422 faceless` — this step only makes sense for `url-based` videos; the type is fixed at creation.\n- **Social-media or unsupported URL** (YouTube, TikTok, Twitter/X, Instagram, Facebook, etc.) → `422 url`.\n- **Page un-parseable or unreachable** → `422`.\n- **Not your video** → `403`.\n\n→ **Next for url-based:** Step B — generate a script from the same URL with `POST /faceless/{faceless}/scrape-script` (or supply your own via `PATCH /faceless/{faceless}`), then configure (`PATCH`) and render."
      }
    },
    "/faceless/{faceless}/scrape-script": {
      "post": {
        "operationId": "scrapeFacelessScript",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "requestBody": {
          "description": "The URL to generate a script from, plus generation options.",
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "url",
                  "duration",
                  "style",
                  "tone",
                  "language"
                ],
                "properties": {
                  "url": {
                    "type": "string",
                    "format": "uri",
                    "description": "Publicly reachable web page URL to extract script content from. Social-media URLs are rejected with `422`.",
                    "example": "https://www.amazon.com/dp/B0CXYZ1234"
                  },
                  "duration": {
                    "type": "integer",
                    "enum": [
                      30,
                      60,
                      180,
                      300,
                      600,
                      900
                    ],
                    "description": "Target length of the generated script in seconds. Must be one of 30, 60, 180, 300, 600, or 900.",
                    "example": 60
                  },
                  "style": {
                    "type": "string",
                    "description": "Narrative style for the generated script (free-form text, max 255 chars). Examples: educational, storytelling, listicle, conversational, motivational.",
                    "example": "educational"
                  },
                  "tone": {
                    "type": "string",
                    "description": "Tone of voice for the generated script. Examples: professional, friendly, casual, authoritative.",
                    "example": "friendly"
                  },
                  "language": {
                    "type": "string",
                    "description": "Language for the generated script (e.g. \"english\").",
                    "example": "english"
                  }
                }
              },
              "example": {
                "url": "https://www.amazon.com/dp/B0CXYZ1234",
                "duration": 60,
                "style": "educational",
                "tone": "friendly",
                "language": "english"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessResource"
                    },
                    "meta": {
                      "type": "object",
                      "properties": {
                        "credits": {
                          "type": "object",
                          "properties": {
                            "cost": {
                              "type": "integer",
                              "description": "The exact credits charged for generating the script from the page content. Matches the `CONTENT_PROMPT_REQUESTED` event amount — the same charge as `PUT /faceless/{faceless}/scripts`."
                            },
                            "remaining": {
                              "type": "integer",
                              "description": "Your credit balance after the charge."
                            }
                          },
                          "required": [
                            "cost",
                            "remaining"
                          ],
                          "description": "Credit balance summary for the user."
                        }
                      },
                      "required": [
                        "credits"
                      ],
                      "description": "Pagination and listing metadata."
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data",
                    "meta"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "video_id": 10,
                    "voice_id": 12,
                    "music_id": null,
                    "background_id": null,
                    "estimated_duration": 60,
                    "type": "url-based",
                    "genre": {
                      "id": 3,
                      "name": "Cinematic",
                      "slug": "cinematic",
                      "active": true
                    },
                    "script": "This product helps you focus throughout the day.",
                    "hash": "abc123",
                    "options": {
                      "aspect_ratio": "9:16"
                    },
                    "is_transcribed": false,
                    "watermark_id": null,
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z",
                    "video": {
                      "id": 10,
                      "user_id": 1,
                      "idea_id": null,
                      "scheduler_id": null,
                      "title": "Focus habits",
                      "type": "faceless",
                      "url": null,
                      "status": "draft",
                      "retries": 0,
                      "hash": "abc123",
                      "synced_at": null,
                      "metadata": {
                        "ai_labels": true,
                        "custom_description": null
                      },
                      "failure": null,
                      "created_at": "2026-01-01T12:00:00.000000Z",
                      "updated_at": "2026-01-01T12:00:00.000000Z"
                    }
                  },
                  "meta": {
                    "credits": {
                      "cost": 5,
                      "remaining": 875
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "402": {
            "$ref": "#/components/responses/PaymentRequired"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "422": {
            "$ref": "#/components/responses/ValidationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "summary": "Scrape a script from a URL",
        "description": "**URL-based flow · Step B · Scrape script** 💳 — generate a narration script from a web page. Charges `CONTENT_PROMPT_REQUESTED` credits (same as `PUT /faceless/{faceless}/scripts`).\n\n💳 Charges credits (`CONTENT_PROMPT_REQUESTED` — the same amount as `PUT /faceless/{faceless}/scripts`). The response `meta.credits` shows the cost and your remaining balance.\n\nGenerates a narration script directly from the content of the supplied web page URL and stores it on the `url-based` faceless video. Use this as an alternative to `PUT /faceless/{faceless}/scripts` when the script should be grounded in page content rather than a free-form topic.\n\n**Note:** this endpoint works on any faceless video type, not just `url-based` — it generates and stores a script regardless of type. You may also skip both scrape-script and `PUT /scripts` and supply your own script verbatim via `PATCH /faceless/{faceless}`.\n\n**Preconditions & common errors:**\n- **No active subscription** → `403` `SUBSCRIPTION-REQUIRED` `An active subscription is required.` — checked before anything else; the public API has no free tier.\n- **Social-media or unsupported URL** → `422 url`.\n- **Page un-parseable or unreachable** → `422`.\n- **Not your video** → `403`.\n- **Insufficient credits** → `402` with code `INSUFFICIENT-CREDITS` and `required` / `available` in the error body.\n- **Missing required fields** (`url`, `duration`, `style`, `tone`, `language`) → `422`.\n\n→ **Next for url-based:** Step 3 — configure voice, captions, and visuals with `PATCH /faceless/{faceless}`, then render."
      }
    },
    "/faceless/{faceless}": {
      "patch": {
        "operationId": "updateFacelessVideo",
        "summary": "Update a faceless video",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/UpdateFacelessRequest"
              },
              "example": {
                "voice_id": 12,
                "genre_id": 3,
                "script": "Three habits that quietly improve your focus.",
                "transition": "fade",
                "captions": {
                  "font_family": "inter",
                  "font_color": "#FFFFFF",
                  "position": "bottom"
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessResource"
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "video_id": 10,
                    "voice_id": 12,
                    "music_id": null,
                    "background_id": null,
                    "estimated_duration": 60,
                    "type": "faceless",
                    "genre": {
                      "id": 3,
                      "name": "Cinematic",
                      "slug": "cinematic",
                      "active": true
                    },
                    "script": "Three habits that quietly improve your focus.",
                    "hash": "abc123",
                    "options": {
                      "aspect_ratio": "9:16"
                    },
                    "is_transcribed": false,
                    "watermark_id": null,
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "422": {
            "$ref": "#/components/responses/ValidationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "**Step 3 of 7 · Configure.**\n\n**Before you can update:** the video must not be busy — you cannot edit it while it is rendering or syncing. Wait until it leaves those states.\n\nUpdates the configuration of a faceless video (script, voice, genre, captions, transitions, and more). Only the fields you send are changed.\n\n**Render-only settings:** the caption `effect` and the `overlay` are **not** updatable here — this endpoint silently ignores them (the request succeeds with `200`, but the stored value is unchanged). Set them in the render request body (`POST /faceless/{faceless}/render`) instead.\n\n→ **Next:** Step 4 — *(optional)* estimate the cost with `GET /faceless/{faceless}/estimate`, or skip to Step 5 — render with `POST /faceless/{faceless}/render`."
      }
    },
    "/faceless/{faceless}/estimate": {
      "get": {
        "operationId": "estimateRenderCredits",
        "summary": "Estimate render credits",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "type": "object",
                      "properties": {
                        "required": {
                          "type": "integer",
                          "description": "The required value for the resource."
                        },
                        "available": {
                          "type": "string",
                          "description": "The available value for the resource."
                        },
                        "sufficient": {
                          "type": "boolean",
                          "description": "The sufficient value for the resource."
                        }
                      },
                      "required": [
                        "required",
                        "available",
                        "sufficient"
                      ],
                      "description": "Estimated required credits, available balance, and whether the balance is sufficient."
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "required": 30,
                    "available": 120,
                    "sufficient": true
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "422": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string"
                    },
                    "error": {
                      "type": "object",
                      "properties": {
                        "code": {
                          "type": "string"
                        },
                        "status": {
                          "type": "integer",
                          "const": 422
                        },
                        "": {
                          "type": "string"
                        }
                      },
                      "required": [
                        "code",
                        "status",
                        null
                      ]
                    }
                  },
                  "required": [
                    "message",
                    "error"
                  ]
                }
              }
            }
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "**Step 4 of 7 · Estimate** *(optional)*.\n\nEstimates the number of credits required to render the given faceless video and compares it against the caller's available balance.\n\n**Before calling:** the faceless must already have a **script** and a **voice** configured. Set them with `PUT /faceless/{faceless}/scripts` (or `PATCH /faceless/{faceless}`) and `PATCH /faceless/{faceless}` (e.g. `{ \"voice_id\": 12 }`). The estimate reads both from the stored faceless — a `?voice_id=` query parameter is **not** accepted and is ignored.\n\n**Common errors:**\n- **No script** (and no voiceover generated yet) → `422` `A script is required before rendering.`\n- **No voice** → `422` `Voice was not provided.` (or `Voice not found.` when the stored `voice_id` does not exist).\n- **Not your video** → `403`.\n\n**Accuracy:** for per-second (clip-engine) renders the estimate is an approximation — the exact charge is computed during rendering and recorded in the credit ledger (`GET /credits/history`), which is the authoritative record of what was charged.\n\n→ **Next:** Step 5 — render with `POST /faceless/{faceless}/render`."
      }
    },
    "/faceless/{faceless}/render": {
      "post": {
        "operationId": "renderFacelessVideo",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "responses": {
          "202": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 202,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessResource"
                    },
                    "meta": {
                      "type": "object",
                      "description": "Present on credit-charging endpoints.",
                      "properties": {
                        "credits": {
                          "type": "object",
                          "description": "Credit accounting for this operation.",
                          "properties": {
                            "cost": {
                              "type": "integer",
                              "description": "The credits that will be charged for this render. The charge runs asynchronously inside the render pipeline; if the render fails before the charge step, nothing is charged. For per-second (clip-engine) renders this is an approximation — the exact charge is computed during rendering, and the credit ledger (`GET /credits/history`) is the authoritative record."
                            },
                            "remaining": {
                              "type": "integer",
                              "description": "Your credit balance. The render charge runs asynchronously (charged renders are refunded if rendering later fails), so this is the pre-charge balance."
                            }
                          }
                        }
                      }
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 202,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "video_id": 10,
                    "voice_id": 12,
                    "music_id": null,
                    "background_id": null,
                    "estimated_duration": 60,
                    "type": "faceless",
                    "genre": {
                      "id": 3,
                      "name": "Cinematic",
                      "slug": "cinematic",
                      "active": true
                    },
                    "script": "Three habits that quietly improve your focus.",
                    "hash": "abc123",
                    "options": {
                      "aspect_ratio": "9:16"
                    },
                    "is_transcribed": false,
                    "watermark_id": null,
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z"
                  },
                  "meta": {
                    "credits": {
                      "cost": 120,
                      "remaining": 880
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "402": {
            "$ref": "#/components/responses/PaymentRequired"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "422": {
            "$ref": "#/components/responses/ValidationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "500": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Whoops! Something went wrong."
                    },
                    "error": {
                      "type": "object",
                      "properties": {
                        "code": {
                          "type": "null"
                        },
                        "status": {
                          "type": "integer",
                          "const": 500
                        },
                        "": {
                          "type": "string"
                        }
                      },
                      "required": [
                        "code",
                        "status",
                        null
                      ]
                    }
                  },
                  "required": [
                    "message",
                    "error"
                  ]
                }
              }
            }
          }
        },
        "summary": "Render a faceless video",
        "x-badges": [
          {
            "name": "Charges credits"
          }
        ],
        "description": "**Step 5 of 7 · Render.**\n\n💳 Charges credits. The response `meta.credits` shows the cost and your remaining balance.\n\n**Before you can render:** first create a faceless video (`POST /faceless`), then generate or supply its script (`PUT /faceless/{faceless}/scripts`) and configure its options — voice, genre, captions, and visuals (`PATCH /faceless/{faceless}`). Optionally call the estimate endpoint first to check the credit cost against your balance.\n\nStarts rendering the faceless video asynchronously and charges the required credits — `meta.credits.cost` is the amount that will be charged once the pipeline reaches the charge step. For per-second clip-engine renders (`ai-clips`) this is an approximation; the exact charge is computed during rendering and recorded in `GET /credits/history` (the authoritative record). Returns immediately with HTTP 202 while generation runs in the background.\n\n**To track progress:** poll `GET /faceless/{id}` — use the faceless **`id`**, not `video_id` — and read `data.video.status` (the `video` object is always embedded). It moves from `rendering` to `completed` (or `failed`). When complete, the playable file is at `data.video.url`; on failure, `data.video.failure` carries the reason. The faceless object itself has no status field; the render lifecycle lives on the embedded `video`. See the **Get your rendered video** guide in the introduction.\n\n**Preconditions & common errors** (checked before any charge):\n- **No script** → `403` `A script is required before rendering.` — set one with `PUT /faceless/{faceless}/scripts` or `PATCH /faceless/{faceless}`.\n- **No voice** → `403` `Voice was not provided.` (or `Voice not found.` when `voice_id` does not exist) — set it with `PATCH /faceless/{faceless}`.\n- **Insufficient credits** → `402` with code `INSUFFICIENT-CREDITS` and `required` / `available` in the error body — check first with `GET /faceless/{faceless}/estimate`.\n- **Video busy** (already rendering or syncing) → `403` `The video is processing currently. Please try again once finished`.\n- **Storage full** → `403` `Please remove some files first` (code `REACH-PLAN-STORAGE-LIMIT`).\n- **No active subscription** → `403` `SUBSCRIPTION-REQUIRED` `An active subscription is required.` — the public API has no free tier; subscribe before generating.\n- **Missing genre** on an `ai-visuals` / `ai-clips` render → `422` `A genre is required for AI visuals and AI clips.`\n- **`url-based` video with no scraped assets** → `422` `assets` — call `POST /faceless/{faceless}/scrape-images` first; without scraped images the render would produce an empty video.\n- **Missing required fields** (`script`, `duration`, `aspect_ratio`) → `422`.\n\n→ **Next:** Step 6 — track progress by polling `GET /faceless/{id}` (use the faceless `id`, not `video_id`).",
        "requestBody": {
          "description": "Render configuration for the faceless video.",
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "script",
                  "duration",
                  "aspect_ratio"
                ],
                "properties": {
                  "script": {
                    "type": "string",
                    "description": "Narration script text for the video."
                  },
                  "duration": {
                    "type": "integer",
                    "description": "Required — target video length in seconds. Any positive integer; not restricted to the script-generation presets (those fixed values apply only to PUT /faceless/{faceless}/scripts)."
                  },
                  "aspect_ratio": {
                    "type": "string",
                    "description": "Output aspect ratio. Allowed values are listed under faceless options (aspect_ratios).",
                    "example": "9:16"
                  },
                  "title": {
                    "type": "string",
                    "maxLength": 255,
                    "description": "Optional title for the video."
                  },
                  "voice_id": {
                    "type": "integer",
                    "description": "Identifier of the narration voice (see faceless options)."
                  },
                  "background_id": {
                    "type": "integer",
                    "description": "Identifier of the background asset (see faceless options)."
                  },
                  "type": {
                    "type": "string",
                    "enum": [
                      "b-roll",
                      "url-based",
                      "ai-visuals",
                      "ai-clips"
                    ],
                    "description": "Faceless video type — controls how the visuals are sourced (stock b-roll, a source URL, AI-generated images, or AI-generated clips)."
                  },
                  "genre_id": {
                    "type": "integer",
                    "description": "Identifier of the genre/style that drives the image-prompt look. REQUIRED for image-based renders (`type` of `ai-visuals` or `ai-clips`); optional for `b-roll` / `url-based` renders that don't use a genre. Allowed values are listed under faceless options (genres).",
                    "example": 3
                  },
                  "character_id": {
                    "type": "integer",
                    "description": "Identifier of the consistent character (see faceless options)."
                  },
                  "image_engine_id": {
                    "type": "integer",
                    "description": "Identifier of the text-to-image engine (see faceless options)."
                  },
                  "clip_engine_id": {
                    "type": "integer",
                    "description": "Identifier of the text-to-video (clip) engine (see faceless options)."
                  },
                  "transition": {
                    "type": "string",
                    "description": "Transition slug applied between scenes. Allowed values are listed under faceless options (transitions)."
                  },
                  "animation": {
                    "type": "string",
                    "description": "Per-image motion effect slug. Allowed values are listed under faceless options (animations)."
                  },
                  "overlay": {
                    "type": "string",
                    "description": "Overlay style slug applied over the video. Allowed values are listed under faceless options (overlays). Render-body-only: set it here (or on export) — `PATCH /faceless/{faceless}` silently ignores it."
                  },
                  "sfx": {
                    "type": "string",
                    "description": "Sound-effect slug applied to the video. Allowed values are listed under faceless options (sfx)."
                  },
                  "ai_labels": {
                    "type": "boolean",
                    "description": "Whether AI-content disclosure labels are applied on publish."
                  },
                  "custom_description": {
                    "type": "string",
                    "maxLength": 255,
                    "description": "Custom caption/description applied to published posts."
                  },
                  "destination_id": {
                    "type": "integer",
                    "description": "Identifier of the destination folder/resource to file the video under."
                  },
                  "captions": {
                    "type": "object",
                    "description": "Caption styling. Only `font_family`, `font_color`, `font_url`, `position`, and `effect` are honored; any other caption keys are ignored.",
                    "properties": {
                      "font_family": {
                        "type": "string",
                        "description": "Caption font family slug (see faceless options)."
                      },
                      "font_color": {
                        "type": "string",
                        "description": "Caption font color as a hex value (e.g. \"#FFFFFF\")."
                      },
                      "font_url": {
                        "type": "string",
                        "description": "URL of a custom font file to use for captions."
                      },
                      "position": {
                        "type": "string",
                        "description": "On-screen caption position slug. Allowed values are listed under faceless options (caption_positions)."
                      },
                      "effect": {
                        "type": "string",
                        "description": "Caption effect slug applied to on-screen text. Allowed values are listed under faceless options (caption_effects). Render-body-only: set it here (or on export) — `PATCH /faceless/{faceless}` silently ignores it."
                      }
                    }
                  },
                  "watermark": {
                    "type": "object",
                    "description": "Watermark image and placement. Provide exactly one source — `id`, `url`, or `file` (mutually exclusive).",
                    "properties": {
                      "id": {
                        "type": "integer",
                        "description": "Identifier of a watermark asset you own. Mutually exclusive with `url` and `file`."
                      },
                      "url": {
                        "type": "string",
                        "description": "Remote URL of the watermark image. Mutually exclusive with `id` and `file`."
                      },
                      "file": {
                        "type": "string",
                        "format": "binary",
                        "description": "Uploaded watermark image file (jpg, jpeg, png, webp; max 5 MB). Mutually exclusive with `id` and `url`."
                      },
                      "position": {
                        "type": "string",
                        "description": "Watermark placement slug. Allowed values are listed under faceless options (watermark_positions)."
                      },
                      "opacity": {
                        "type": "integer",
                        "minimum": 0,
                        "maximum": 100,
                        "description": "Watermark opacity as a percentage (0–100)."
                      }
                    }
                  },
                  "music_id": {
                    "type": "integer",
                    "description": "Identifier of a background music track (media id). Mutually exclusive with `music.url` and `music.file`."
                  },
                  "music": {
                    "type": "object",
                    "description": "Background music source. Provide exactly one of `url` or `file`, and only when `music_id` is omitted (all three are mutually exclusive).",
                    "properties": {
                      "url": {
                        "type": "string",
                        "description": "Remote URL of a music track. Mutually exclusive with `music_id` and `music.file`."
                      },
                      "file": {
                        "type": "string",
                        "format": "binary",
                        "description": "Uploaded music file (mp3, wav, aac, m4a, ogg; max 20 MB). Mutually exclusive with `music_id` and `music.url`."
                      }
                    }
                  },
                  "volume": {
                    "type": "string",
                    "enum": [
                      "low",
                      "medium",
                      "high"
                    ],
                    "description": "Background-music volume level. Required when any music source is set."
                  },
                  "publications": {
                    "type": "array",
                    "description": "Social posts to schedule for the rendered video.",
                    "items": {
                      "type": "object",
                      "properties": {
                        "channel_id": {
                          "type": "integer",
                          "description": "Identifier of the connected social channel to publish to."
                        },
                        "scheduled_at": {
                          "type": "string",
                          "format": "date-time",
                          "description": "Future timestamp to publish the post, or null to publish immediately."
                        }
                      }
                    }
                  },
                  "assets": {
                    "type": "array",
                    "description": "Explicit ordered media assets to compose the video from. Orders must start at 0 and be consecutive with no gaps.",
                    "items": {
                      "type": "object",
                      "required": [
                        "id",
                        "order"
                      ],
                      "properties": {
                        "id": {
                          "type": "integer",
                          "description": "Identifier of the media asset."
                        },
                        "order": {
                          "type": "integer",
                          "minimum": 0,
                          "description": "Zero-based position of the asset in the sequence."
                        }
                      }
                    }
                  }
                }
              },
              "example": {
                "script": "Three small habits that quietly improve your focus every day.",
                "duration": 60,
                "aspect_ratio": "9:16",
                "type": "ai-visuals",
                "title": "Focus habits",
                "voice_id": 12,
                "genre_id": 3,
                "image_engine_id": 1,
                "clip_engine_id": 2,
                "transition": "fade",
                "animation": "pan-in",
                "overlay": "none",
                "sfx": "whoosh",
                "volume": "medium",
                "music_id": 8,
                "captions": {
                  "font_family": "inter",
                  "font_color": "#FFFFFF",
                  "position": "bottom",
                  "effect": "highlight"
                },
                "watermark": {
                  "id": 42,
                  "position": "bottom-right",
                  "opacity": 80
                },
                "publications": [
                  {
                    "channel_id": 5,
                    "scheduled_at": "2025-02-01T18:30:00Z"
                  }
                ],
                "assets": [
                  {
                    "id": 101,
                    "order": 0
                  },
                  {
                    "id": 102,
                    "order": 1
                  }
                ]
              }
            }
          }
        }
      }
    },
    "/faceless/{id}": {
      "get": {
        "operationId": "getFacelessVideo",
        "summary": "Get a faceless video",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "id",
            "in": "path",
            "required": true,
            "schema": {
              "type": "integer"
            },
            "description": "Identifier of the faceless video.",
            "example": 1
          },
          {
            "name": "include",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Comma-separated list of related resources to embed. Allowed values: `video`, `captions`, `media`, `music`, `voice`, `background`, `genre`, `watermark`, `character`, `assets`. Any other value is rejected with `400 Bad Request`. Note that `video` is always embedded in the response — you never need `include` to read render progress.",
            "example": "captions,voice"
          }
        ],
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessResource"
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "video_id": 10,
                    "voice_id": 12,
                    "music_id": null,
                    "background_id": null,
                    "estimated_duration": 60,
                    "type": "faceless",
                    "genre": {
                      "id": 3,
                      "name": "Cinematic",
                      "slug": "cinematic",
                      "active": true
                    },
                    "script": "Three habits that quietly improve your focus.",
                    "hash": "abc123",
                    "options": {
                      "aspect_ratio": "9:16"
                    },
                    "is_transcribed": false,
                    "watermark_id": null,
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z",
                    "video": {
                      "id": 10,
                      "user_id": 1,
                      "idea_id": null,
                      "scheduler_id": null,
                      "title": "Focus habits",
                      "type": "faceless",
                      "url": "https://cdn.syllaby.dev/videos/10/final.mp4",
                      "status": "completed",
                      "retries": 0,
                      "hash": "abc123",
                      "synced_at": "2026-01-01T12:05:00.000000Z",
                      "metadata": {
                        "ai_labels": true,
                        "custom_description": null
                      },
                      "failure": null,
                      "created_at": "2026-01-01T12:00:00.000000Z",
                      "updated_at": "2026-01-01T12:00:00.000000Z"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "**Step 6 of 7 · Track progress.**\n\nReturns a single faceless video you own. The render state is always embedded under `data.video` — no `include` needed: `url` (null until the render completes), `status`, and `failure` (`code` + `message`, non-null only when the render failed).\n\nUse the `include` query parameter to embed further related resources; values outside the documented allowlist are rejected with `400 Bad Request`.\n\nResponds with `404 Not Found` when the id does not exist **or** belongs to another account. Make sure you pass the faceless **`id`** (from the create/render response), not `video_id` — they are different identifiers, and polling with `video_id` is the most common cause of unexpected 404s.\n\n→ **Next:** when `data.video.status` is `completed`, you have your video — *(optional)* Step 7, export a restyled cut with `POST /faceless/{faceless}/export`. If it is `failed`, retry with `POST /faceless/{faceless}/retry`."
      }
    },
    "/faceless/{faceless}/retry": {
      "post": {
        "operationId": "retryFacelessRender",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "responses": {
          "202": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 202,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessResource"
                    },
                    "meta": {
                      "type": "object",
                      "description": "Present on credit-charging endpoints.",
                      "properties": {
                        "credits": {
                          "type": "object",
                          "description": "Credit accounting for this operation.",
                          "properties": {
                            "cost": {
                              "type": "integer",
                              "description": "The credits charged for the retry. For a video that had already been exported this is the exact export-fix amount charged (`0` when nothing qualified for a charge). For an un-exported video the charge runs asynchronously, so this is the preflight estimate that will be charged."
                            },
                            "remaining": {
                              "type": "integer",
                              "description": "Your credit balance at the time of the response. When the charge runs asynchronously (retry of an un-exported video) this is the pre-charge balance."
                            }
                          }
                        }
                      }
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 202,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "video_id": 10,
                    "voice_id": 12,
                    "music_id": null,
                    "background_id": null,
                    "estimated_duration": 60,
                    "type": "faceless",
                    "genre": {
                      "id": 3,
                      "name": "Cinematic",
                      "slug": "cinematic",
                      "active": true
                    },
                    "script": "Three habits that quietly improve your focus.",
                    "hash": "abc123",
                    "options": {
                      "aspect_ratio": "9:16"
                    },
                    "is_transcribed": false,
                    "watermark_id": null,
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z",
                    "video": {
                      "id": 10,
                      "user_id": 1,
                      "idea_id": null,
                      "scheduler_id": null,
                      "title": "Focus habits",
                      "type": "faceless",
                      "url": null,
                      "status": "rendering",
                      "retries": 1,
                      "hash": "abc123",
                      "synced_at": null,
                      "metadata": {
                        "ai_labels": true,
                        "custom_description": null
                      },
                      "failure": null,
                      "created_at": "2026-01-01T12:00:00.000000Z",
                      "updated_at": "2026-01-01T12:00:00.000000Z"
                    }
                  },
                  "meta": {
                    "credits": {
                      "cost": 120,
                      "remaining": 880
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "402": {
            "$ref": "#/components/responses/PaymentRequired"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "summary": "Retry a faceless render",
        "x-badges": [
          {
            "name": "Charges credits"
          }
        ],
        "description": "**Step 6 of 7 · Track progress — retry a failed render.**\n\n💳 Charges credits. The response `meta.credits` shows the cost and your remaining balance.\n\n**Before you can retry:** the embedded video must have **failed** — fetch `GET /faceless/{id}` and check that `data.video.status` is `failed` (the reason is in `data.video.failure`). The video must also not be busy (rendering or syncing). Retry does nothing for drafts or already-completed videos.\n\nRe-attempts rendering for a faceless video that previously failed. Returns HTTP 202 with the video state embedded under `data.video` while the retry runs asynchronously; track it the same way as render.\n\n**Credits:** for a video that had already been exported, `meta.credits.cost` is the exact export-fix amount charged — `0` when nothing qualified for a charge. For a video that has not been exported, the charge runs asynchronously inside the render pipeline, so `cost` is the preflight estimate that will be charged.\n\n**Preconditions & common errors:**\n- **Video not in a failed state** → `403` `Only failed videos can be re-tried. Please create a new video instead.` — only a `failed` render can be retried.\n- **Video busy** (rendering or syncing) → `403` `The video is still being processed. Please wait until it is finished.`\n- **Insufficient credits** → `402` with code `INSUFFICIENT-CREDITS` and `required` / `available` in the error body.\n- **Not your video** → `403` `You are not allowed to re-generate this video`.\n\n→ **Next:** keep polling `GET /faceless/{id}` until `data.video.status` is `completed`."
      }
    },
    "/faceless/{faceless}/export": {
      "post": {
        "operationId": "exportFacelessVideo",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "requestBody": {
          "description": "Restyling options for the export. All fields are optional; omit a field to keep the rendered video's current styling. Note: unlike render, the watermark accepts only an existing asset `id` (no upload), and music is selected by `music_id` only.",
          "required": false,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "transition": {
                    "type": "string",
                    "description": "Transition slug applied between scenes. Allowed values are listed under faceless options (transitions)."
                  },
                  "overlay": {
                    "type": "string",
                    "description": "Overlay style slug applied over the video. Allowed values are listed under faceless options (overlays)."
                  },
                  "sfx": {
                    "type": "string",
                    "description": "Sound-effect slug applied to the video. Allowed values are listed under faceless options (sfx)."
                  },
                  "music_id": {
                    "type": "integer",
                    "description": "Identifier of a background music track (media id)."
                  },
                  "volume": {
                    "type": "string",
                    "enum": [
                      "low",
                      "medium",
                      "high"
                    ],
                    "description": "Background-music volume level. Required when `music_id` is set."
                  },
                  "captions": {
                    "type": "object",
                    "description": "Caption styling. Only `font_family`, `font_color`, `font_url`, `position`, and `effect` are honored; any other caption keys are ignored.",
                    "properties": {
                      "font_family": {
                        "type": "string",
                        "description": "Caption font family slug (see faceless options)."
                      },
                      "font_color": {
                        "type": "string",
                        "description": "Caption font color as a hex value (e.g. \"#FFFFFF\")."
                      },
                      "font_url": {
                        "type": "string",
                        "description": "URL of a custom font file to use for captions."
                      },
                      "position": {
                        "type": "string",
                        "description": "On-screen caption position slug. Allowed values are listed under faceless options (caption_positions)."
                      },
                      "effect": {
                        "type": "string",
                        "description": "Caption effect slug applied to on-screen text. Allowed values are listed under faceless options (caption_effects)."
                      }
                    }
                  },
                  "watermark": {
                    "type": "object",
                    "description": "Watermark asset and placement. References an existing asset you own.",
                    "properties": {
                      "id": {
                        "type": "integer",
                        "description": "Identifier of a watermark asset you own."
                      },
                      "position": {
                        "type": "string",
                        "description": "Watermark placement slug. Allowed values are listed under faceless options (watermark_positions)."
                      },
                      "opacity": {
                        "type": "integer",
                        "minimum": 0,
                        "maximum": 100,
                        "description": "Watermark opacity as a percentage (0–100)."
                      }
                    }
                  }
                }
              },
              "example": {
                "transition": "fade",
                "volume": "medium",
                "captions": {
                  "font_family": "inter",
                  "font_color": "#FFFFFF",
                  "position": "bottom",
                  "effect": "highlight"
                },
                "watermark": {
                  "id": 42,
                  "position": "bottom-right",
                  "opacity": 80
                }
              }
            }
          }
        },
        "responses": {
          "202": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 202,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessResource"
                    },
                    "meta": {
                      "type": "object",
                      "description": "Present on credit-charging endpoints.",
                      "properties": {
                        "credits": {
                          "type": "object",
                          "description": "Credit accounting for this operation.",
                          "properties": {
                            "cost": {
                              "type": "integer",
                              "description": "The exact credits charged for this export — `0` when nothing changed enough to charge (unchanged options, music, and watermark)."
                            },
                            "remaining": {
                              "type": "integer",
                              "description": "Your credit balance after the charge."
                            }
                          }
                        }
                      }
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 202,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "video_id": 10,
                    "voice_id": 12,
                    "music_id": null,
                    "background_id": null,
                    "estimated_duration": 60,
                    "type": "faceless",
                    "genre": {
                      "id": 3,
                      "name": "Cinematic",
                      "slug": "cinematic",
                      "active": true
                    },
                    "script": "Three habits that quietly improve your focus.",
                    "hash": "abc123",
                    "options": {
                      "aspect_ratio": "9:16"
                    },
                    "is_transcribed": false,
                    "watermark_id": null,
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z",
                    "video": {
                      "id": 10,
                      "user_id": 1,
                      "idea_id": null,
                      "scheduler_id": null,
                      "title": "Focus habits",
                      "type": "faceless",
                      "url": null,
                      "status": "rendering",
                      "retries": 0,
                      "hash": "abc123",
                      "synced_at": null,
                      "metadata": {
                        "ai_labels": true,
                        "custom_description": null
                      },
                      "failure": null,
                      "created_at": "2026-01-01T12:00:00.000000Z",
                      "updated_at": "2026-01-01T12:00:00.000000Z"
                    }
                  },
                  "meta": {
                    "credits": {
                      "cost": 50,
                      "remaining": 830
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "402": {
            "$ref": "#/components/responses/PaymentRequired"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "422": {
            "$ref": "#/components/responses/ValidationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          },
          "500": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Internal Error"
                    },
                    "error": {
                      "type": "object",
                      "properties": {
                        "code": {
                          "type": "null"
                        },
                        "status": {
                          "type": "integer",
                          "const": 500
                        },
                        "": {
                          "type": "string"
                        }
                      },
                      "required": [
                        "code",
                        "status",
                        null
                      ]
                    }
                  },
                  "required": [
                    "message",
                    "error"
                  ]
                }
              }
            }
          }
        },
        "summary": "Export a faceless video",
        "x-badges": [
          {
            "name": "Charges credits"
          }
        ],
        "description": "**Step 7 of 7 · Export a restyled cut** *(optional)*.\n\n💳 Charges credits. The response `meta.credits` shows the cost and your remaining balance.\n\n**Before you can export:** the video must already be rendered, and must not currently be busy (rendering or syncing).\n\nRebuilds the rendered faceless video source with the supplied styling (captions, watermark, music, transitions) and queues an export. Returns HTTP 202 with the video state embedded under `data.video` while the export runs asynchronously.\n\n**Credits:** `meta.credits.cost` is the exact amount charged — `0` when nothing changed enough to charge (unchanged options, music, and watermark).\n\n**Preconditions & common errors:**\n- **Video busy** (rendering or syncing) → `403` `The video is still being processed`.\n- **Not your video** → `403` `You are not allowed to export this video`.\n- **Insufficient credits** (only when the restyle qualifies for a charge) → `402` with code `INSUFFICIENT-CREDITS`.\n\n→ This is the final step. Track the export the same way — poll `GET /faceless/{id}`."
      }
    },
    "/faceless/{faceless}/assets": {
      "get": {
        "operationId": "listFacelessAssets",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          },
          {
            "name": "index",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Zero-based scene position; returns only the asset at that position.",
            "example": 0
          }
        ],
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/App.Http.Resources.Api.v2.AssetResource"
                      },
                      "description": "The faceless video's ordered media assets."
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": [
                    {
                      "id": 1,
                      "user_id": 1,
                      "type": "faceless_background",
                      "status": "success",
                      "order": 0,
                      "media": [
                        {
                          "id": 5,
                          "name": "scene-1",
                          "file_name": "scene-1.png",
                          "mime_type": "image/png",
                          "extension": "png",
                          "download_url": "https://cdn.syllaby.dev/assets/scene-1.png"
                        }
                      ],
                      "created_at": "2026-01-01T12:00:00.000000Z",
                      "updated_at": "2026-01-01T12:00:00.000000Z"
                    }
                  ]
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "summary": "List faceless assets",
        "description": "**Reference** — inspect rendered assets (populated after Step 6).\n\nLists the media assets (images, clips) that make up the faceless video, ordered by scene. Pass `index` to fetch the asset at a single scene position.\n\n**Note:** assets are produced during rendering — expect an empty list until the video has been rendered at least once."
      }
    },
    "/faceless/{faceless}/assets/{asset}": {
      "get": {
        "operationId": "getFacelessAsset",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "faceless",
            "in": "path",
            "required": true,
            "description": "The faceless ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          },
          {
            "name": "asset",
            "in": "path",
            "required": true,
            "description": "The asset ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/App.Http.Resources.Api.v2.AssetResource"
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "type": "faceless_background",
                    "status": "success",
                    "order": 0,
                    "media": [
                      {
                        "id": 5,
                        "name": "scene-1",
                        "file_name": "scene-1.png",
                        "mime_type": "image/png",
                        "extension": "png",
                        "download_url": "https://cdn.syllaby.dev/assets/scene-1.png"
                      }
                    ],
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "summary": "Get a faceless asset",
        "description": "**Reference** — inspect a single rendered asset (populated after Step 6).\n\nReturns a single media asset belonging to the faceless video."
      }
    },
    "/presets/faceless": {
      "get": {
        "operationId": "listFacelessPresets",
        "summary": "List faceless presets",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "include",
            "in": "query",
            "schema": {
              "type": "string"
            },
            "description": "Comma-separated list of related resources to embed. Allowed values: `music`, `voice`, `background`, `watermark`, `genre`. Any other value is rejected with `400 Bad Request`.",
            "example": "music,voice"
          }
        ],
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "anyOf": [
                    {
                      "type": "object",
                      "properties": {
                        "message": {
                          "type": "string",
                          "const": "Success.",
                          "description": "Human-readable status message for the response."
                        },
                        "status": {
                          "type": "integer",
                          "const": 200,
                          "description": "HTTP status code echoed in the response body."
                        },
                        "data": {
                          "type": "array",
                          "items": {
                            "$ref": "#/components/schemas/FacelessPresetResource"
                          },
                          "description": "The authenticated user's saved faceless presets."
                        }
                      },
                      "required": [
                        "message",
                        "status",
                        "data"
                      ]
                    },
                    {
                      "type": "object",
                      "properties": {
                        "message": {
                          "type": "string",
                          "const": "Success.",
                          "description": "Human-readable status message for the response."
                        },
                        "status": {
                          "type": "integer",
                          "const": 200,
                          "description": "HTTP status code echoed in the response body."
                        },
                        "data": {
                          "type": "array",
                          "items": {
                            "type": "string"
                          },
                          "minItems": 0,
                          "maxItems": 0,
                          "additionalItems": false,
                          "description": "The authenticated user's saved faceless presets."
                        }
                      },
                      "required": [
                        "message",
                        "status",
                        "data"
                      ]
                    }
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": [
                    {
                      "id": 1,
                      "user_id": 1,
                      "name": "My default preset",
                      "voice_id": 12,
                      "genre_id": 3,
                      "orientation": "portrait",
                      "font_family": "inter",
                      "font_color": "#FFFFFF",
                      "volume": "medium",
                      "created_at": "2026-01-01T12:00:00.000000Z",
                      "updated_at": "2026-01-01T12:00:00.000000Z"
                    }
                  ]
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequired"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "**Reusable presets** — saved defaults you can apply at Step 1 (Create).\n\nLists the authenticated user's saved faceless presets, newest first. A preset bundles reusable defaults (voice, genre, captions, watermark, etc.) you can apply when creating videos.\n\nUse the `include` query parameter to embed related resources; values outside the documented allowlist are rejected with `400 Bad Request`."
      },
      "post": {
        "operationId": "createFacelessPreset",
        "summary": "Create a faceless preset",
        "tags": [
          "Faceless Videos"
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ManageFacelessPresetRequest"
              },
              "example": {
                "name": "My default preset",
                "voice_id": 12,
                "genre_id": 3,
                "orientation": "portrait",
                "font_family": "inter",
                "font_color": "#FFFFFF",
                "volume": "medium"
              }
            }
          }
        },
        "responses": {
          "201": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 201,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessPresetResource"
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 201,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "name": "My default preset",
                    "voice_id": 12,
                    "genre_id": 3,
                    "orientation": "portrait",
                    "font_family": "inter",
                    "font_color": "#FFFFFF",
                    "volume": "medium",
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequired"
          },
          "422": {
            "$ref": "#/components/responses/ValidationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "**Reusable presets** — saved defaults you can apply at Step 1 (Create).\n\nCreates a reusable faceless preset for the authenticated user from the supplied defaults.\n\n**`name` is required on create** — omitting it returns `422`. (On update, `PATCH /presets/faceless/{preset}`, `name` is optional.) All other fields are optional; `duration` must be a positive integer (≥ 1) and `font_color` must be either `default` or a hex value (e.g. `#ffffff`)."
      }
    },
    "/presets/faceless/{preset}": {
      "patch": {
        "operationId": "updateFacelessPreset",
        "summary": "Update a faceless preset",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "preset",
            "in": "path",
            "required": true,
            "description": "The preset ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "requestBody": {
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ManageFacelessPresetRequest"
              },
              "example": {
                "name": "Updated preset",
                "voice_id": 14,
                "volume": "high"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "message": {
                      "type": "string",
                      "const": "Success.",
                      "description": "Human-readable status message for the response."
                    },
                    "status": {
                      "type": "integer",
                      "const": 200,
                      "description": "HTTP status code echoed in the response body."
                    },
                    "data": {
                      "$ref": "#/components/schemas/FacelessPresetResource"
                    }
                  },
                  "required": [
                    "message",
                    "status",
                    "data"
                  ]
                },
                "example": {
                  "message": "Success.",
                  "status": 200,
                  "data": {
                    "id": 1,
                    "user_id": 1,
                    "name": "My default preset",
                    "voice_id": 12,
                    "genre_id": 3,
                    "orientation": "portrait",
                    "font_family": "inter",
                    "font_color": "#FFFFFF",
                    "volume": "medium",
                    "created_at": "2026-01-01T12:00:00.000000Z",
                    "updated_at": "2026-01-01T12:00:00.000000Z"
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "422": {
            "$ref": "#/components/responses/ValidationException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "description": "**Reusable presets.**\n\nUpdates a faceless preset you own. Only the fields you send are changed."
      },
      "delete": {
        "operationId": "deleteFacelessPreset",
        "tags": [
          "Faceless Videos"
        ],
        "parameters": [
          {
            "name": "preset",
            "in": "path",
            "required": true,
            "description": "The preset ID",
            "schema": {
              "type": "integer"
            },
            "example": 1
          }
        ],
        "responses": {
          "204": {
            "description": "No content"
          },
          "401": {
            "$ref": "#/components/responses/AuthenticationException"
          },
          "403": {
            "$ref": "#/components/responses/SubscriptionRequiredOrAuthorization"
          },
          "404": {
            "$ref": "#/components/responses/ModelNotFoundException"
          },
          "429": {
            "$ref": "#/components/responses/TooManyRequests"
          }
        },
        "summary": "Delete a faceless preset",
        "description": "**Reusable presets.**\n\nPermanently deletes a faceless preset you own. Responds with HTTP 204 on success."
      }
    }
  },
  "components": {
    "securitySchemes": {
      "http": {
        "type": "http",
        "scheme": "bearer"
      }
    },
    "schemas": {
      "AccountPublicationResource": {
        "type": "object",
        "properties": {
          "status": {
            "type": "string",
            "description": "Current lifecycle status of the resource."
          },
          "error": {
            "type": "string",
            "description": "Error message describing why processing failed, if any."
          },
          "metadata": {
            "type": "string",
            "description": "Additional metadata for the resource."
          },
          "post_type": {
            "type": "string",
            "description": "Type of social post (e.g. \"reel\", \"short\", \"post\")."
          },
          "channels": {
            "$ref": "#/components/schemas/SocialChannelResource"
          }
        },
        "required": [
          "status",
          "error",
          "metadata",
          "post_type",
          "channels"
        ],
        "title": "AccountPublicationResource",
        "description": "A account Publication record."
      },
      "App.Http.Resources.Api.v2.AssetResource": {
        "type": "object",
        "description": "A media asset (image or clip) that composes a faceless video scene.",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Identifier of the asset."
          },
          "uuid": {
            "type": "string",
            "description": "Stable UUID of the asset within the video (present when listed against a scene)."
          },
          "type": {
            "type": "string",
            "enum": [
              "audios",
              "faceless-background",
              "ai-image",
              "ai-video",
              "stock-video",
              "stock-image",
              "custom-image",
              "custom-video",
              "scraped",
              "watermark",
              "thumbnail",
              "font"
            ],
            "description": "Kind of media asset (e.g. \"ai-image\", \"ai-video\", \"stock-video\")."
          },
          "status": {
            "type": "string",
            "enum": [
              "draft",
              "success",
              "failed",
              "processing",
              "unknown"
            ],
            "description": "Generation lifecycle state of the asset."
          },
          "url": {
            "type": "string",
            "nullable": true,
            "description": "Downloadable URL of the rendered media file, when available."
          },
          "order": {
            "type": "integer",
            "description": "Zero-based scene position of the asset within the video."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the asset was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the asset was last updated."
          }
        },
        "required": [
          "id",
          "type",
          "status",
          "created_at",
          "updated_at"
        ],
        "title": "App.Http.Resources.Api.v2.AssetResource"
      },
      "App.Http.Resources.FacelessResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "integer",
            "description": "Identifier of the owning user."
          },
          "video_id": {
            "type": "integer",
            "description": "Identifier of the parent video."
          },
          "voice_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the narration voice (see faceless options)."
          },
          "music_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the background music track (media id)."
          },
          "background_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the background asset (see faceless options)."
          },
          "estimated_duration": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Estimated rendered duration in seconds."
          },
          "type": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/FacelessType"
              },
              {
                "type": "null"
              }
            ],
            "description": "Type/category discriminator for the resource."
          },
          "genre": {
            "$ref": "#/components/schemas/GenreResource"
          },
          "script": {
            "type": [
              "string",
              "null"
            ],
            "description": "Narration script text for the video."
          },
          "hash": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Opaque content hash used for change detection."
          },
          "options": {
            "type": [
              "string",
              "null"
            ],
            "description": "Additional generation options for the faceless video."
          },
          "is_transcribed": {
            "type": "boolean",
            "description": "Whether the video audio has been transcribed."
          },
          "watermark_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the watermark asset (must be owned by the caller)."
          },
          "watermark": {
            "$ref": "#/components/schemas/AssetResource"
          },
          "character_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the consistent character (see faceless options)."
          },
          "character": {
            "$ref": "#/components/schemas/CharacterResource"
          },
          "image_engine_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the text-to-image engine (see faceless options)."
          },
          "clip_engine_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the text-to-video (clip) engine (see faceless options)."
          },
          "engines": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "minItems": 0,
            "maxItems": 0,
            "additionalItems": false,
            "description": "Available inference engines."
          },
          "video": {
            "$ref": "#/components/schemas/VideoResource"
          },
          "generator": {
            "$ref": "#/components/schemas/GeneratorResource"
          },
          "background": {
            "$ref": "#/components/schemas/AssetResource"
          },
          "media": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/MediaResource"
            },
            "description": "Underlying media files attached to the resource."
          },
          "music": {
            "$ref": "#/components/schemas/MediaResource"
          },
          "voice": {
            "$ref": "#/components/schemas/VoiceResource"
          },
          "trackers": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TrackerResource"
            },
            "description": "Tracking records for the resource."
          },
          "assets": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/AssetResource"
            },
            "description": "Ordered list of media assets used to compose the video."
          },
          "captions": {
            "$ref": "#/components/schemas/CaptionResource"
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "video_id",
          "voice_id",
          "music_id",
          "background_id",
          "estimated_duration",
          "type",
          "script",
          "hash",
          "options",
          "is_transcribed",
          "watermark_id",
          "character_id",
          "image_engine_id",
          "clip_engine_id",
          "engines",
          "created_at",
          "updated_at"
        ],
        "title": "App.Http.Resources.FacelessResource",
        "description": "A faceless record."
      },
      "AssetResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "uuid": {
            "type": "string",
            "description": "Globally unique UUID for the resource."
          },
          "user_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the owning user."
          },
          "parent_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the parent record, or null."
          },
          "provider_id": {
            "type": [
              "string",
              "null"
            ],
            "description": "Provider-side identifier for the resource."
          },
          "genre_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the genre/style (see faceless options)."
          },
          "name": {
            "type": [
              "string",
              "null"
            ],
            "description": "Display name of the resource."
          },
          "type": {
            "$ref": "#/components/schemas/AssetType"
          },
          "slug": {
            "type": [
              "string",
              "null"
            ],
            "description": "URL-friendly unique identifier for the resource."
          },
          "description": {
            "type": [
              "string",
              "null"
            ],
            "description": "Human-readable description of the resource."
          },
          "model": {
            "type": [
              "string",
              "null"
            ],
            "description": "Underlying model name used to generate the resource."
          },
          "style": {
            "type": [
              "string",
              "null"
            ],
            "description": "Style label applied to generation."
          },
          "status": {
            "$ref": "#/components/schemas/AssetStatus"
          },
          "is_private": {
            "type": "integer",
            "description": "Whether the record is private to its owner."
          },
          "orientation": {
            "type": [
              "string",
              "null"
            ],
            "description": "Video orientation. One of \"landscape\", \"portrait\", or \"square\"."
          },
          "order": {
            "type": "string",
            "description": "Zero-based ordering position within its collection."
          },
          "active": {
            "type": "string",
            "description": "Whether the record is currently active and selectable."
          },
          "is_bookmarked": {
            "type": "boolean",
            "description": "Whether the caller has bookmarked this record."
          },
          "is_used": {
            "type": "boolean",
            "description": "Whether the asset is currently in use by a video."
          },
          "media": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/MediaResource"
            },
            "description": "Underlying media files attached to the resource."
          },
          "genre": {
            "$ref": "#/components/schemas/Genre"
          },
          "user": {
            "$ref": "#/components/schemas/User"
          },
          "videos": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Faceless"
            },
            "description": "Videos associated with the resource."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "parent_id",
          "provider_id",
          "genre_id",
          "name",
          "type",
          "slug",
          "description",
          "model",
          "style",
          "status",
          "is_private",
          "orientation",
          "is_bookmarked",
          "is_used",
          "created_at",
          "updated_at"
        ],
        "title": "AssetResource",
        "description": "A asset record."
      },
      "AssetStatus": {
        "type": "string",
        "enum": [
          "draft",
          "success",
          "failed",
          "processing",
          "unknown"
        ],
        "title": "AssetStatus",
        "description": "A asset Status record."
      },
      "AssetType": {
        "type": "string",
        "enum": [
          "audios",
          "faceless-background",
          "ai-image",
          "ai-video",
          "stock-video",
          "stock-image",
          "custom-image",
          "custom-video",
          "scraped",
          "watermark",
          "thumbnail",
          "font"
        ],
        "title": "AssetType",
        "description": "A asset Type record."
      },
      "CaptionResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "integer",
            "description": "Identifier of the owning user."
          },
          "model_id": {
            "type": "integer",
            "description": "Identifier of the related model the media is attached to."
          },
          "model_type": {
            "type": "string",
            "description": "Class/type of the related model the media is attached to."
          },
          "content": {
            "type": "array",
            "items": {},
            "description": "Text content of the resource."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "model_id",
          "model_type",
          "content",
          "created_at",
          "updated_at"
        ],
        "title": "CaptionResource",
        "description": "A caption record."
      },
      "CharacterResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "uuid": {
            "type": "string",
            "description": "Globally unique UUID for the resource."
          },
          "user_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the owning user."
          },
          "genre": {
            "$ref": "#/components/schemas/GenreResource"
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "slug": {
            "type": "string",
            "description": "URL-friendly unique identifier for the resource."
          },
          "description": {
            "type": [
              "string",
              "null"
            ],
            "description": "Human-readable description of the resource."
          },
          "training_images": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Images used to train the consistent character."
          },
          "gender": {
            "type": "string",
            "description": "Gender label (e.g. \"male\", \"female\", \"neutral\")."
          },
          "status": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/CharacterStatus"
              },
              {
                "type": "null"
              }
            ],
            "description": "Current lifecycle status of the resource."
          },
          "meta": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Pagination and listing metadata."
          },
          "active": {
            "type": "integer",
            "description": "Whether the record is currently active and selectable."
          },
          "reference": {
            "$ref": "#/components/schemas/MediaResource"
          },
          "thumbnail": {
            "$ref": "#/components/schemas/MediaResource"
          },
          "preview": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/MediaResource"
            },
            "description": "URL of a preview image or clip for the resource."
          },
          "created_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "uuid",
          "user_id",
          "name",
          "slug",
          "description",
          "training_images",
          "gender",
          "status",
          "meta",
          "active",
          "created_at",
          "updated_at"
        ],
        "title": "CharacterResource",
        "description": "A character record."
      },
      "CharacterStatus": {
        "type": "string",
        "enum": [
          "draft",
          "preview-generating",
          "preview-ready",
          "preview-failed",
          "pose-generating",
          "pose-ready",
          "pose-failed",
          "model-training",
          "model-training-failed",
          "ready"
        ],
        "title": "CharacterStatus",
        "description": "A character Status record."
      },
      "CreateFacelessRequest": {
        "type": "object",
        "description": "v2 public-API input contract for creating a faceless video.\nInherits v1 rules; override here when the public contract must diverge.",
        "properties": {
          "title": {
            "type": "string",
            "maxLength": 255,
            "description": "Title of the resource."
          },
          "type": {
            "type": "string",
            "enum": [
              "b-roll",
              "url-based",
              "ai-visuals",
              "ai-clips"
            ],
            "description": "Faceless video type — controls how the visuals are sourced: `b-roll` (stock footage), `url-based` (images scraped from a web page — requires `POST /faceless/{faceless}/scrape-images` before render), `ai-visuals` (AI-generated images), or `ai-clips` (AI-generated video clips). Defaults to `ai-visuals`. **The type is fixed at creation and cannot be changed later.**"
          },
          "idea_id": {
            "type": "integer",
            "description": "Identifier of a content idea created in the Syllaby app, linking the video to it. Optional — omit it for API-only flows; the v2 API exposes no ideas endpoints, so there is no way to obtain a valid id through the API."
          },
          "starts_at": {
            "type": "string",
            "format": "date-time",
            "description": "Optional ISO-8601 timestamp that schedules the video on your Syllaby content calendar — sending it creates a calendar event for the video. It does not delay or schedule the render."
          },
          "ends_at": {
            "type": "string",
            "format": "date-time",
            "description": "Optional ISO-8601 timestamp marking the end of the scheduled calendar slot. Must be the same as or after `starts_at`; only meaningful together with it."
          }
        },
        "title": "CreateFacelessRequest",
        "required": [
          "title",
          "type"
        ]
      },
      "EngineResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "slug": {
            "type": "string",
            "description": "URL-friendly unique identifier for the resource."
          },
          "description": {
            "type": [
              "string",
              "null"
            ],
            "description": "Human-readable description of the resource."
          },
          "type": {
            "type": "string",
            "description": "Type/category discriminator for the resource."
          },
          "cost": {
            "type": "array",
            "items": {},
            "description": "Credit cost charged for one use of this engine/feature."
          },
          "modifiers": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Style or generation modifiers applied."
          },
          "features": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Feature flags or entitlements enabled for the plan."
          },
          "flags": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Feature flags applied to the user."
          },
          "order": {
            "type": "integer",
            "description": "Zero-based ordering position within its collection."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "name",
          "slug",
          "description",
          "type",
          "cost",
          "modifiers",
          "features",
          "flags",
          "order",
          "created_at",
          "updated_at"
        ],
        "title": "EngineResource",
        "description": "A engine record."
      },
      "EventResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "integer",
            "description": "Identifier of the owning user."
          },
          "scheduler_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the owning scheduler."
          },
          "color": {
            "type": [
              "string",
              "null"
            ],
            "description": "Hex color value (e.g. \"#FFFFFF\")."
          },
          "model_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the related model the media is attached to."
          },
          "model_type": {
            "type": [
              "string",
              "null"
            ],
            "description": "Class/type of the related model the media is attached to."
          },
          "starts_at": {
            "type": "string",
            "description": "ISO-8601 timestamp marking the start of the period."
          },
          "ends_at": {
            "type": "string",
            "description": "ISO-8601 timestamp marking the end of the period."
          },
          "completed_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when processing completed, or null."
          },
          "cancelled_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was cancelled, or null."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          },
          "user": {
            "$ref": "#/components/schemas/UserResource"
          },
          "": {
            "type": "object",
            "description": "The  value for the resource."
          },
          "scheduler": {
            "$ref": "#/components/schemas/SchedulerResource"
          }
        },
        "required": [
          "id",
          "user_id",
          "scheduler_id",
          "color",
          "model_id",
          "model_type",
          "starts_at",
          "ends_at",
          "completed_at",
          "cancelled_at",
          "created_at",
          "updated_at"
        ],
        "title": "EventResource",
        "description": "A event record."
      },
      "ExportFacelessRequest": {
        "type": "object",
        "properties": {
          "transition": {
            "type": "string",
            "enum": [
              "slide-left",
              "slide-right",
              "slide-up",
              "slide-down",
              "scale-in",
              "scale-out",
              "zoom-in",
              "zoom-out",
              "rotate-left",
              "rotate-right",
              "fade",
              "none",
              "mixed",
              "pop",
              "dreamy",
              "swing",
              "spin-right",
              "spin-left",
              "swoosh-left",
              "swoosh-right",
              "glide-left",
              "glide-right",
              "drop",
              "tumble-left",
              "tumble-right",
              "float",
              "rise-left",
              "rise-right",
              "bounce",
              "flash",
              "crossfade",
              "blur-dissolve",
              "zoom-dissolve"
            ],
            "description": "Transition slug applied between scenes (see faceless options)."
          },
          "overlay": {
            "type": "string",
            "enum": [
              "none",
              "vhs",
              "rain",
              "glitch",
              "dust",
              "sparkling-gold",
              "spark-effect",
              "abstract-particles"
            ],
            "description": "Overlay style slug applied over the video (see faceless options)."
          },
          "sfx": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "none",
              "whoosh"
            ],
            "description": "Sound-effect slug applied to the video (see faceless options)."
          },
          "volume": {
            "type": "string",
            "enum": [
              "low",
              "medium",
              "high"
            ],
            "description": "Background-music volume level: \"low\", \"medium\", or \"high\"."
          },
          "music_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the background music track (media id)."
          },
          "transcriptions": {
            "type": "array",
            "items": {
              "type": "array",
              "items": {
                "type": "string"
              },
              "minItems": 1
            },
            "description": "Per-scene transcription overrides keyed by scene."
          },
          "captions": {
            "type": "object",
            "properties": {
              "font_family": {
                "type": [
                  "string",
                  "null"
                ],
                "description": "Caption font family slug (see faceless options)."
              },
              "font_url": {
                "type": [
                  "string",
                  "null"
                ],
                "format": "uri",
                "description": "URL of a custom font file to use for captions."
              },
              "font_color": {
                "type": [
                  "string",
                  "null"
                ],
                "description": "Caption font color as a hex value (e.g. \"#FFFFFF\")."
              },
              "position": {
                "type": "string",
                "enum": [
                  "top",
                  "bottom",
                  "center"
                ],
                "description": "On-screen position slug (e.g. \"bottom\", \"center\", \"top\")."
              },
              "effect": {
                "type": "string",
                "enum": [
                  "karaoke",
                  "highlight",
                  "fade",
                  "bounce",
                  "slide",
                  "enlarge"
                ],
                "description": "Caption effect slug applied to on-screen text (see faceless options)."
              }
            },
            "description": "Caption styling options (font, color, position, effect)."
          },
          "watermark": {
            "type": "object",
            "properties": {
              "id": {
                "type": [
                  "integer",
                  "null"
                ],
                "description": "Unique numeric identifier of the resource."
              },
              "position": {
                "type": [
                  "string",
                  "null"
                ],
                "enum": [
                  "top-left",
                  "top-center",
                  "top-right",
                  "middle-left",
                  "middle-center",
                  "middle-right",
                  "bottom-left",
                  "bottom-center",
                  "bottom-right",
                  "none"
                ],
                "description": "On-screen position slug (e.g. \"bottom\", \"center\", \"top\")."
              },
              "opacity": {
                "type": [
                  "integer",
                  "null"
                ],
                "minimum": 0,
                "maximum": 100,
                "description": "Watermark opacity as a percentage (0–100)."
              }
            },
            "description": "Watermark image and placement options."
          }
        },
        "title": "ExportFacelessRequest",
        "description": "A export Faceless Request record."
      },
      "Faceless": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "integer",
            "description": "Identifier of the owning user."
          },
          "type": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/FacelessType"
              },
              {
                "type": "null"
              }
            ],
            "description": "Type/category discriminator for the resource."
          },
          "video_id": {
            "type": "integer",
            "description": "Identifier of the parent video."
          },
          "voice_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the narration voice (see faceless options)."
          },
          "background_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the background asset (see faceless options)."
          },
          "music_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the background music track (media id)."
          },
          "watermark_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the watermark asset (must be owned by the caller)."
          },
          "estimated_duration": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Estimated rendered duration in seconds."
          },
          "is_transcribed": {
            "type": "boolean",
            "description": "Whether the video audio has been transcribed."
          },
          "genre_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the genre/style (see faceless options)."
          },
          "character_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the consistent character (see faceless options)."
          },
          "script": {
            "type": [
              "string",
              "null"
            ],
            "description": "Narration script text for the video."
          },
          "hash": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Opaque content hash used for change detection."
          },
          "options": {
            "type": [
              "string",
              "null"
            ],
            "description": "Additional generation options for the faceless video."
          },
          "batch": {
            "type": [
              "string",
              "null"
            ],
            "description": "Identifier grouping records created in the same batch operation."
          },
          "created_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was last updated."
          },
          "brief": {
            "type": [
              "string",
              "null"
            ],
            "description": "Short brief or summary text for the content."
          },
          "image_engine_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the text-to-image engine (see faceless options)."
          },
          "clip_engine_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the text-to-video (clip) engine (see faceless options)."
          }
        },
        "required": [
          "id",
          "user_id",
          "type",
          "video_id",
          "voice_id",
          "background_id",
          "music_id",
          "watermark_id",
          "estimated_duration",
          "is_transcribed",
          "genre_id",
          "character_id",
          "script",
          "hash",
          "options",
          "batch",
          "created_at",
          "updated_at",
          "brief",
          "image_engine_id",
          "clip_engine_id"
        ],
        "title": "Faceless",
        "description": "A faceless record."
      },
      "FacelessPresetResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Unique numeric identifier of the resource."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "user_id": {
            "type": "string",
            "description": "Identifier of the owning user."
          },
          "user": {
            "$ref": "#/components/schemas/UserResource"
          },
          "music_id": {
            "type": "string",
            "description": "Identifier of the background music track (media id)."
          },
          "music": {
            "$ref": "#/components/schemas/MediaResource"
          },
          "music_category_id": {
            "type": "string",
            "description": "Identifier of the music category tag."
          },
          "music_category": {
            "$ref": "#/components/schemas/TagResource"
          },
          "voice_id": {
            "type": "string",
            "description": "Identifier of the narration voice (see faceless options)."
          },
          "voice": {
            "$ref": "#/components/schemas/VoiceResource"
          },
          "background_id": {
            "type": "string",
            "description": "Identifier of the background asset (see faceless options)."
          },
          "background": {
            "$ref": "#/components/schemas/AssetResource"
          },
          "resource_id": {
            "type": "string",
            "description": "Identifier of the destination resource/folder."
          },
          "resource": {
            "$ref": "#/components/schemas/FolderWithContentResource"
          },
          "genre_id": {
            "type": "string",
            "description": "Identifier of the genre/style (see faceless options)."
          },
          "genre": {
            "$ref": "#/components/schemas/GenreResource"
          },
          "image_engine_id": {
            "type": "string",
            "description": "Identifier of the text-to-image engine (see faceless options)."
          },
          "image_engine": {
            "$ref": "#/components/schemas/EngineResource"
          },
          "clip_engine_id": {
            "type": "string",
            "description": "Identifier of the text-to-video (clip) engine (see faceless options)."
          },
          "clip_engine": {
            "$ref": "#/components/schemas/EngineResource"
          },
          "language": {
            "type": "string",
            "description": "Language of the content (e.g. \"english\")."
          },
          "font_family": {
            "type": "string",
            "description": "Caption font family slug (see faceless options)."
          },
          "font_color": {
            "type": "string",
            "description": "Caption font color as a hex value (e.g. \"#FFFFFF\")."
          },
          "position": {
            "type": "string",
            "description": "On-screen position slug (e.g. \"bottom\", \"center\", \"top\")."
          },
          "caption_animation": {
            "type": "string",
            "description": "Caption animation/effect slug applied to on-screen captions."
          },
          "duration": {
            "type": "integer",
            "description": "Target video length in seconds."
          },
          "orientation": {
            "type": "string",
            "description": "Video orientation. One of \"landscape\", \"portrait\", or \"square\"."
          },
          "transition": {
            "type": "string",
            "description": "Transition slug applied between scenes (see faceless options)."
          },
          "animation": {
            "type": "string",
            "description": "Per-image motion effect slug (e.g. \"zoom-in\"). See faceless options."
          },
          "volume": {
            "type": "string",
            "description": "Background-music volume level: \"low\", \"medium\", or \"high\"."
          },
          "sfx": {
            "type": "string",
            "description": "Sound-effect slug applied to the video (see faceless options)."
          },
          "overlay": {
            "type": "string",
            "description": "Overlay style slug applied over the video (see faceless options)."
          },
          "watermark_id": {
            "type": "string",
            "description": "Identifier of the watermark asset (must be owned by the caller)."
          },
          "watermark": {
            "$ref": "#/components/schemas/AssetResource"
          },
          "watermark_position": {
            "type": "string",
            "description": "Watermark placement slug (e.g. \"bottom-right\")."
          },
          "watermark_opacity": {
            "type": "string",
            "description": "Watermark opacity as a percentage (0–100)."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "name",
          "user_id",
          "music_id",
          "music_category_id",
          "voice_id",
          "background_id",
          "resource_id",
          "genre_id",
          "image_engine_id",
          "clip_engine_id",
          "language",
          "font_family",
          "font_color",
          "position",
          "caption_animation",
          "duration",
          "orientation",
          "transition",
          "animation",
          "volume",
          "sfx",
          "overlay",
          "watermark_id",
          "watermark_position",
          "watermark_opacity",
          "created_at",
          "updated_at"
        ],
        "title": "FacelessPresetResource",
        "description": "A faceless Preset record."
      },
      "FacelessResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "string",
            "description": "Identifier of the owning user."
          },
          "video_id": {
            "type": "string",
            "description": "Identifier of the parent video."
          },
          "voice_id": {
            "type": "string",
            "description": "Identifier of the narration voice (see faceless options)."
          },
          "music_id": {
            "type": "string",
            "description": "Identifier of the background music track (media id)."
          },
          "background_id": {
            "type": "string",
            "description": "Identifier of the background asset (see faceless options)."
          },
          "estimated_duration": {
            "type": "string",
            "description": "Estimated rendered duration in seconds."
          },
          "type": {
            "type": "string",
            "description": "Type/category discriminator for the resource."
          },
          "genre_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the selected genre/style (see faceless options). Matches `genre.id` when the genre relation is loaded."
          },
          "genre": {
            "allOf": [
              {
                "$ref": "#/components/schemas/GenreResource"
              }
            ],
            "description": "The selected genre/style, embedded when the `genre` relation is loaded; otherwise omitted."
          },
          "script": {
            "type": "string",
            "description": "Narration script text for the video."
          },
          "hash": {
            "type": "string",
            "description": "Opaque content hash used for change detection."
          },
          "options": {
            "type": "string",
            "description": "Additional generation options for the faceless video."
          },
          "is_transcribed": {
            "type": "string",
            "description": "Whether the video audio has been transcribed."
          },
          "watermark_id": {
            "type": "string",
            "description": "Identifier of the watermark asset (must be owned by the caller)."
          },
          "watermark": {
            "$ref": "#/components/schemas/AssetResource"
          },
          "character_id": {
            "type": "string",
            "description": "Identifier of the consistent character (see faceless options)."
          },
          "character": {
            "$ref": "#/components/schemas/CharacterResource"
          },
          "image_engine_id": {
            "type": "string",
            "description": "Identifier of the text-to-image engine (see faceless options)."
          },
          "clip_engine_id": {
            "type": "string",
            "description": "Identifier of the text-to-video (clip) engine (see faceless options)."
          },
          "engines": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "minItems": 0,
            "maxItems": 0,
            "additionalItems": false,
            "description": "Available inference engines."
          },
          "video": {
            "$ref": "#/components/schemas/VideoResource"
          },
          "generator": {
            "$ref": "#/components/schemas/GeneratorResource"
          },
          "background": {
            "$ref": "#/components/schemas/AssetResource"
          },
          "media": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/MediaResource"
            },
            "description": "Underlying media files attached to the resource."
          },
          "music": {
            "$ref": "#/components/schemas/MediaResource"
          },
          "voice": {
            "$ref": "#/components/schemas/VoiceResource"
          },
          "trackers": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TrackerResource"
            },
            "description": "Tracking records for the resource."
          },
          "assets": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/AssetResource"
            },
            "description": "Ordered list of media assets used to compose the video."
          },
          "captions": {
            "$ref": "#/components/schemas/CaptionResource"
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "video_id",
          "voice_id",
          "music_id",
          "background_id",
          "estimated_duration",
          "type",
          "script",
          "hash",
          "options",
          "is_transcribed",
          "watermark_id",
          "character_id",
          "image_engine_id",
          "clip_engine_id",
          "engines",
          "created_at",
          "updated_at"
        ],
        "title": "FacelessResource",
        "description": "A faceless record."
      },
      "FacelessType": {
        "type": "string",
        "enum": [
          "b-roll",
          "url-based",
          "ai-visuals",
          "ai-clips"
        ],
        "title": "FacelessType",
        "description": "A faceless Type record."
      },
      "FolderResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "integer",
            "description": "Identifier of the owning user."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "color": {
            "type": [
              "string",
              "null"
            ],
            "description": "Hex color value (e.g. \"#FFFFFF\")."
          },
          "is_bookmarked": {
            "type": "boolean",
            "description": "Whether the caller has bookmarked this record."
          },
          "created_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "name",
          "color",
          "is_bookmarked",
          "created_at",
          "updated_at"
        ],
        "title": "FolderResource",
        "description": "A folder record."
      },
      "FolderWithContentResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "integer",
            "description": "Identifier of the owning user."
          },
          "model_id": {
            "type": "integer",
            "description": "Identifier of the related model the media is attached to."
          },
          "model_type": {
            "type": "string",
            "description": "Class/type of the related model the media is attached to."
          },
          "model": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/FolderResource"
              },
              {
                "$ref": "#/components/schemas/VideoResource"
              },
              {
                "type": "null"
              }
            ],
            "description": "Underlying model name used to generate the resource."
          },
          "is_root": {
            "type": "boolean",
            "description": "Whether the folder is a top-level (root) folder."
          },
          "parent": {
            "$ref": "#/components/schemas/FolderWithContentResource"
          },
          "children": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/FolderWithContentResource"
            },
            "description": "Direct child records nested under this one."
          },
          "ancestors": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/FolderWithContentResource"
            },
            "description": "Parent folders in the hierarchy, ordered from root to direct parent."
          },
          "descendants": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/FolderWithContentResource"
            },
            "description": "All nested descendant records beneath this one."
          },
          "children_count": {
            "type": "string",
            "description": "Number of direct child records."
          },
          "created_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "model_id",
          "model_type",
          "is_root",
          "children_count",
          "created_at",
          "updated_at"
        ],
        "title": "FolderWithContentResource",
        "description": "A folder With Content record."
      },
      "GenerateFacelessScriptRequest": {
        "type": "object",
        "properties": {
          "style": {
            "type": "string",
            "maxLength": 255,
            "description": "Required — narrative style for the generated script (free-form text, max 255 chars). Examples: educational, storytelling, listicle, conversational, motivational."
          },
          "tone": {
            "type": "string",
            "maxLength": 255,
            "description": "Tone of voice for generated content (e.g. \"professional\")."
          },
          "language": {
            "type": "string",
            "maxLength": 255,
            "description": "Language of the content (e.g. \"english\")."
          },
          "topic": {
            "type": "string",
            "maxLength": 500,
            "description": "Topic or subject of the content."
          },
          "duration": {
            "type": "integer",
            "description": "Target length of the generated script in seconds. Must be one of 30, 60, 180, 300, 600, or 900.",
            "enum": [
              30,
              60,
              180,
              300,
              600,
              900
            ]
          }
        },
        "required": [
          "style",
          "tone",
          "language",
          "topic",
          "duration"
        ],
        "title": "GenerateFacelessScriptRequest",
        "description": "A generate Faceless Script Request record."
      },
      "GeneratorResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "model_id": {
            "type": "integer",
            "description": "Identifier of the related model the media is attached to."
          },
          "model_type": {
            "type": "string",
            "description": "Class/type of the related model the media is attached to."
          },
          "topic": {
            "type": [
              "string",
              "null"
            ],
            "description": "Topic or subject of the content."
          },
          "length": {
            "type": [
              "string",
              "null"
            ],
            "description": "Length of the content."
          },
          "tone": {
            "type": [
              "string",
              "null"
            ],
            "description": "Tone of voice for generated content (e.g. \"professional\")."
          },
          "style": {
            "type": [
              "string",
              "null"
            ],
            "description": "Style label applied to generation."
          },
          "language": {
            "type": [
              "string",
              "null"
            ],
            "description": "Language of the content (e.g. \"english\")."
          },
          "context": {
            "type": "array",
            "items": {},
            "description": "Additional contextual metadata for the resource."
          },
          "output": {
            "type": [
              "string",
              "null"
            ],
            "description": "Generated output payload."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "model_id",
          "model_type",
          "topic",
          "length",
          "tone",
          "style",
          "language",
          "context",
          "output",
          "created_at",
          "updated_at"
        ],
        "title": "GeneratorResource",
        "description": "A generator record."
      },
      "Genre": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "slug": {
            "type": "string",
            "description": "URL-friendly unique identifier for the resource."
          },
          "character_prompt": {
            "type": [
              "string",
              "null"
            ],
            "description": "Prompt describing the consistent character's appearance."
          },
          "meta": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Pagination and listing metadata."
          },
          "active": {
            "type": "integer",
            "description": "Whether the record is currently active and selectable."
          },
          "order": {
            "type": "integer",
            "description": "Zero-based ordering position within its collection."
          },
          "consistent_character": {
            "type": "boolean",
            "description": "Whether the genre supports a consistent character across scenes."
          },
          "created_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "name",
          "slug",
          "character_prompt",
          "meta",
          "active",
          "order",
          "consistent_character",
          "created_at",
          "updated_at"
        ],
        "title": "Genre",
        "description": "A genre record."
      },
      "GenreResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "slug": {
            "type": "string",
            "description": "URL-friendly unique identifier for the resource."
          },
          "active": {
            "type": "integer",
            "description": "Whether the record is currently active and selectable."
          },
          "consistent_character": {
            "type": "boolean",
            "description": "Whether the genre supports a consistent character across scenes."
          },
          "has_prompt": {
            "type": "boolean",
            "description": "Whether the genre accepts a custom image prompt."
          },
          "preview": {
            "type": "array",
            "items": {},
            "description": "URL of a preview image or clip for the resource."
          },
          "created_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "name",
          "slug",
          "active",
          "consistent_character",
          "has_prompt",
          "preview",
          "created_at",
          "updated_at"
        ],
        "title": "GenreResource",
        "description": "A genre record."
      },
      "IdeaResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "keyword_id": {
            "type": "integer",
            "description": "Identifier of the keyword."
          },
          "keyword": {
            "$ref": "#/components/schemas/KeywordResource"
          },
          "title": {
            "type": [
              "string",
              "null"
            ],
            "description": "Title of the resource."
          },
          "slug": {
            "type": [
              "string",
              "null"
            ],
            "description": "URL-friendly unique identifier for the resource."
          },
          "trend": {
            "type": [
              "number",
              "null"
            ],
            "description": "Trend direction (e.g. \"up\", \"down\", \"flat\")."
          },
          "country": {
            "type": [
              "string",
              "null"
            ],
            "description": "Two-letter country code (ISO 3166-1 alpha-2)."
          },
          "currency": {
            "type": [
              "string",
              "null"
            ],
            "description": "Three-letter currency code (ISO 4217, e.g. \"USD\")."
          },
          "locale": {
            "type": [
              "string",
              "null"
            ],
            "description": "BCP-47 locale code (e.g. \"en-US\")."
          },
          "volume": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Background-music volume level: \"low\", \"medium\", or \"high\"."
          },
          "cpc": {
            "type": [
              "number",
              "null"
            ],
            "description": "Estimated cost-per-click for the keyword, in USD."
          },
          "competition": {
            "type": [
              "number",
              "null"
            ],
            "description": "Keyword competition score (0–1, higher means more competitive)."
          },
          "competition_label": {
            "type": [
              "string",
              "null"
            ],
            "description": "Human-readable competition band (e.g. \"LOW\", \"MEDIUM\", \"HIGH\")."
          },
          "total_results": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Total number of results matching the query."
          },
          "trends": {
            "type": [
              "string",
              "null"
            ],
            "description": "Time-series trend data points."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "keyword_id",
          "title",
          "slug",
          "trend",
          "country",
          "currency",
          "locale",
          "volume",
          "cpc",
          "competition",
          "competition_label",
          "total_results",
          "trends",
          "created_at",
          "updated_at"
        ],
        "title": "IdeaResource",
        "description": "A idea record."
      },
      "KeywordResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "slug": {
            "type": [
              "string",
              "null"
            ],
            "description": "URL-friendly unique identifier for the resource."
          },
          "network": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/Networks"
              },
              {
                "type": "null"
              }
            ],
            "description": "Social network identifier (e.g. \"tiktok\", \"youtube\")."
          },
          "source": {
            "type": [
              "string",
              "null"
            ],
            "description": "Source/origin of the resource."
          },
          "metrics": {
            "type": "object",
            "properties": {
              "trend": {
                "type": "number",
                "description": "Trend direction (e.g. \"up\", \"down\", \"flat\")."
              },
              "cpc": {
                "type": "object",
                "properties": {
                  "min": {
                    "type": "number",
                    "description": "Minimum value of the range."
                  },
                  "max": {
                    "type": "number",
                    "description": "Maximum value of the range."
                  }
                },
                "required": [
                  "min",
                  "max"
                ],
                "description": "Estimated cost-per-click for the keyword, in USD."
              },
              "volume": {
                "type": "object",
                "properties": {
                  "min": {
                    "type": "integer",
                    "description": "Minimum value of the range."
                  },
                  "max": {
                    "type": "integer",
                    "description": "Maximum value of the range."
                  }
                },
                "required": [
                  "min",
                  "max"
                ],
                "description": "Background-music volume level: \"low\", \"medium\", or \"high\"."
              },
              "competition": {
                "type": "object",
                "properties": {
                  "min": {
                    "type": "number",
                    "description": "Minimum value of the range."
                  },
                  "max": {
                    "type": "number",
                    "description": "Maximum value of the range."
                  }
                },
                "required": [
                  "min",
                  "max"
                ],
                "description": "Keyword competition score (0–1, higher means more competitive)."
              }
            },
            "required": [
              "trend",
              "cpc",
              "volume",
              "competition"
            ],
            "description": "Performance metrics for the resource."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "name",
          "slug",
          "network",
          "source",
          "created_at",
          "updated_at"
        ],
        "title": "KeywordResource",
        "description": "A keyword record."
      },
      "ManageFacelessPresetRequest": {
        "type": "object",
        "properties": {
          "name": {
            "type": "string",
            "maxLength": 255,
            "description": "Display name of the preset. **Required when creating** (`POST /presets/faceless`); **optional when updating** (`PATCH /presets/faceless/{preset}`) — OpenAPI cannot make `required` depend on the HTTP verb, so it is listed in `required` here and the create-only rule is documented in this note and the create operation's description."
          },
          "volume": {
            "type": [
              "string",
              "null"
            ],
            "maxLength": 50,
            "description": "Background-music volume level: \"low\", \"medium\", or \"high\"."
          },
          "language": {
            "type": [
              "string",
              "null"
            ],
            "maxLength": 50,
            "description": "Language of the content (e.g. \"english\")."
          },
          "font_color": {
            "type": [
              "string",
              "null"
            ],
            "maxLength": 50,
            "description": "Caption font color — either the literal `default` or a hex value (3- or 6-digit, e.g. `#ffffff` or `#fff`).",
            "pattern": "^(default|#([0-9a-fA-F]{3}|[0-9a-fA-F]{6}))$",
            "example": "#ffffff"
          },
          "font_family": {
            "type": [
              "string",
              "null"
            ],
            "maxLength": 50,
            "description": "Caption font family slug (see faceless options)."
          },
          "duration": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Target video length in seconds — a positive number of seconds.",
            "minimum": 1
          },
          "orientation": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "landscape",
              "portrait",
              "square"
            ],
            "maxLength": 26,
            "description": "Video orientation. One of \"landscape\", \"portrait\", or \"square\"."
          },
          "position": {
            "type": [
              "string",
              "null"
            ],
            "maxLength": 50,
            "description": "On-screen position slug (e.g. \"bottom\", \"center\", \"top\")."
          },
          "caption_animation": {
            "type": [
              "string",
              "null"
            ],
            "maxLength": 50,
            "description": "Caption animation/effect slug applied to on-screen captions."
          },
          "sfx": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "none",
              "whoosh"
            ],
            "maxLength": 50,
            "description": "Sound-effect slug applied to the video (see faceless options)."
          },
          "music_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the background music track (media id)."
          },
          "music_category_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the music category tag."
          },
          "background_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the background asset (see faceless options)."
          },
          "genre_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the genre/style (see faceless options)."
          },
          "voice_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the narration voice (see faceless options)."
          },
          "transition": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "slide-left",
              "slide-right",
              "slide-up",
              "slide-down",
              "scale-in",
              "scale-out",
              "zoom-in",
              "zoom-out",
              "rotate-left",
              "rotate-right",
              "fade",
              "none",
              "mixed",
              "pop",
              "dreamy",
              "swing",
              "spin-right",
              "spin-left",
              "swoosh-left",
              "swoosh-right",
              "glide-left",
              "glide-right",
              "drop",
              "tumble-left",
              "tumble-right",
              "float",
              "rise-left",
              "rise-right",
              "bounce",
              "flash",
              "crossfade",
              "blur-dissolve",
              "zoom-dissolve"
            ],
            "maxLength": 50,
            "description": "Transition slug applied between scenes (see faceless options)."
          },
          "animation": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "pan-in",
              "pan-out",
              "pan-left",
              "pan-right",
              "pan-up",
              "pan-down",
              "rotate-left-in",
              "rotate-right-in",
              "float",
              "none",
              "mixed"
            ],
            "maxLength": 50,
            "description": "Per-image motion effect slug (e.g. \"zoom-in\"). See faceless options."
          },
          "overlay": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "none",
              "vhs",
              "rain",
              "glitch",
              "dust",
              "sparkling-gold",
              "spark-effect",
              "abstract-particles"
            ],
            "maxLength": 50,
            "description": "Overlay style slug applied over the video (see faceless options)."
          },
          "watermark_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the watermark asset (must be owned by the caller)."
          },
          "watermark_position": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "top-left",
              "top-center",
              "top-right",
              "middle-left",
              "middle-center",
              "middle-right",
              "bottom-left",
              "bottom-center",
              "bottom-right",
              "none"
            ],
            "description": "Watermark placement slug (e.g. \"bottom-right\")."
          },
          "watermark_opacity": {
            "type": [
              "integer",
              "null"
            ],
            "minimum": 0,
            "maximum": 100,
            "description": "Watermark opacity as a percentage (0–100)."
          },
          "resource_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the destination resource/folder."
          },
          "image_engine_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the text-to-image engine (see faceless options)."
          },
          "clip_engine_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the text-to-video (clip) engine (see faceless options)."
          }
        },
        "title": "ManageFacelessPresetRequest",
        "description": "A manage Faceless Preset Request record. `name` is required when creating a preset (`POST /presets/faceless`) and optional when updating one (`PATCH /presets/faceless/{preset}`); all other fields are optional in both cases.",
        "required": [
          "name"
        ]
      },
      "MeResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "email": {
            "type": "string",
            "description": "The user's email address."
          },
          "email_verified": {
            "type": "boolean",
            "description": "Whether the user has verified their email address."
          },
          "credits": {
            "type": "object",
            "properties": {
              "remaining": {
                "type": "integer",
                "description": "Remaining monthly credits available to spend."
              },
              "total": {
                "type": "integer",
                "description": "Total monthly credit allotment."
              },
              "extra": {
                "type": "integer",
                "description": "Extra (top-up) credits available beyond the monthly allotment."
              }
            },
            "required": [
              "remaining",
              "total",
              "extra"
            ],
            "description": "Credit balance summary for the user."
          },
          "subscription": {
            "anyOf": [
              {
                "type": "object",
                "properties": {
                  "exists": {
                    "type": "boolean",
                    "description": "Whether a subscription exists for the user."
                  },
                  "active": {
                    "type": "string",
                    "description": "Whether the record is currently active and selectable."
                  },
                  "trial": {
                    "type": "string",
                    "description": "Whether the subscription is currently in a trial period."
                  },
                  "plan": {
                    "type": "string",
                    "description": "Name of the user's current subscription plan, or null."
                  },
                  "ends_at": {
                    "type": "string",
                    "description": "ISO-8601 timestamp marking the end of the period."
                  }
                },
                "required": [
                  "exists",
                  "active",
                  "trial",
                  "plan",
                  "ends_at"
                ]
              },
              {
                "type": "object",
                "properties": {
                  "exists": {
                    "type": "boolean",
                    "description": "Whether a subscription exists for the user."
                  },
                  "active": {
                    "type": "boolean",
                    "description": "Whether the record is currently active and selectable."
                  },
                  "trial": {
                    "type": "boolean",
                    "description": "Whether the subscription is currently in a trial period."
                  },
                  "plan": {
                    "type": "null",
                    "description": "Name of the user's current subscription plan, or null."
                  },
                  "ends_at": {
                    "type": "null",
                    "description": "ISO-8601 timestamp marking the end of the period."
                  }
                },
                "required": [
                  "exists",
                  "active",
                  "trial",
                  "plan",
                  "ends_at"
                ]
              }
            ],
            "description": "High-level subscription state for the user."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "name",
          "email",
          "email_verified",
          "credits",
          "subscription",
          "created_at",
          "updated_at"
        ],
        "title": "MeResource",
        "description": "A me record."
      },
      "MediaResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the owning user."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "file_name": {
            "type": "string",
            "description": "Stored file name of the media asset."
          },
          "uuid": {
            "type": [
              "string",
              "null"
            ],
            "description": "Globally unique UUID for the resource."
          },
          "collection": {
            "type": "string",
            "description": "Media-library collection the file belongs to."
          },
          "model_id": {
            "type": "integer",
            "description": "Identifier of the related model the media is attached to."
          },
          "model_type": {
            "type": "string",
            "description": "Class/type of the related model the media is attached to."
          },
          "original_url": {
            "type": "string",
            "description": "Permanent source URL of the media file."
          },
          "download_url": {
            "type": [
              "string",
              "null"
            ],
            "description": "Temporary signed URL to download the media file."
          },
          "order": {
            "type": "integer",
            "description": "Zero-based ordering position within its collection."
          },
          "mime_type": {
            "type": [
              "string",
              "null"
            ],
            "description": "MIME type of the media file (e.g. \"video/mp4\")."
          },
          "extension": {
            "type": "string",
            "description": "File extension (e.g. \"mp4\", \"png\")."
          },
          "size": {
            "type": "integer",
            "description": "File size in bytes."
          },
          "conversions": {
            "type": [
              "object",
              "null"
            ],
            "additionalProperties": {},
            "description": "Number of tracked conversions."
          },
          "custom_properties": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Arbitrary key/value metadata attached to the media file."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "name",
          "file_name",
          "uuid",
          "collection",
          "model_id",
          "model_type",
          "original_url",
          "download_url",
          "order",
          "mime_type",
          "extension",
          "size",
          "conversions",
          "custom_properties",
          "created_at",
          "updated_at"
        ],
        "title": "MediaResource",
        "description": "A media record."
      },
      "Networks": {
        "type": "string",
        "enum": [
          "google",
          "google-trends",
          "youtube",
          "instagram",
          "twitter",
          "bing",
          "pinterest",
          "tiktok"
        ],
        "title": "Networks",
        "description": "A networks record."
      },
      "PublicationResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "name": {
            "type": [
              "string",
              "null"
            ],
            "description": "Display name of the resource."
          },
          "scheduled_at": {
            "type": "string",
            "description": "ISO-8601 timestamp the post is scheduled to publish, or null."
          },
          "draft": {
            "type": "boolean",
            "description": "Whether the record is an unpublished draft."
          },
          "temporary": {
            "type": "boolean",
            "description": "Whether the resource is temporary and may be purged."
          },
          "video_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the parent video."
          },
          "script": {
            "type": [
              "string",
              "null"
            ],
            "description": "Narration script text for the video."
          },
          "media": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/PublicationResource"
            },
            "description": "Underlying media files attached to the resource."
          },
          "accounts": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/AccountPublicationResource"
            },
            "description": "Connected social accounts associated with this resource."
          },
          "video": {
            "$ref": "#/components/schemas/VideoResource"
          },
          "event": {
            "$ref": "#/components/schemas/EventResource"
          },
          "aggregate": {
            "type": "object",
            "properties": {
              "views-count": {
                "anyOf": [
                  {
                    "type": "string"
                  },
                  {
                    "type": "integer",
                    "enum": [
                      0
                    ]
                  }
                ],
                "description": "Number of views on the published post."
              },
              "likes-count": {
                "anyOf": [
                  {
                    "type": "string"
                  },
                  {
                    "type": "integer",
                    "enum": [
                      0
                    ]
                  }
                ],
                "description": "Number of likes on the published post."
              },
              "comments-count": {
                "anyOf": [
                  {
                    "type": "string"
                  },
                  {
                    "type": "integer",
                    "enum": [
                      0
                    ]
                  }
                ],
                "description": "Number of comments on the published post."
              }
            },
            "required": [
              "views-count",
              "likes-count",
              "comments-count"
            ],
            "description": "Aggregated metric totals for the resource."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "name",
          "draft",
          "temporary",
          "video_id",
          "script",
          "media",
          "aggregate",
          "created_at",
          "updated_at"
        ],
        "title": "PublicationResource",
        "description": "A publication record."
      },
      "SceneResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "uuid": {
            "type": "string",
            "description": "Globally unique UUID for the resource."
          },
          "video_prompt": {
            "type": [
              "string",
              "null"
            ],
            "description": "Prompt used to generate the video clip."
          },
          "order": {
            "type": "integer",
            "description": "Zero-based ordering position within its collection."
          },
          "role": {
            "type": [
              "string",
              "null"
            ],
            "description": "The user's role within the account."
          },
          "status": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/SceneStatus"
              },
              {
                "type": "null"
              }
            ],
            "description": "Current lifecycle status of the resource."
          },
          "error": {
            "type": [
              "string",
              "null"
            ],
            "description": "Error message describing why processing failed, if any."
          },
          "first_frame_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the first-frame asset."
          },
          "first_frame": {
            "$ref": "#/components/schemas/AssetResource"
          },
          "last_frame_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the last-frame asset."
          },
          "last_frame": {
            "$ref": "#/components/schemas/AssetResource"
          },
          "clip_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the generated clip."
          },
          "clip": {
            "$ref": "#/components/schemas/AssetResource"
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "uuid",
          "video_prompt",
          "order",
          "role",
          "status",
          "error",
          "first_frame_id",
          "last_frame_id",
          "clip_id",
          "created_at",
          "updated_at"
        ],
        "title": "SceneResource",
        "description": "A scene record."
      },
      "SceneStatus": {
        "type": "string",
        "enum": [
          "draft",
          "clip:queued",
          "clip:generating",
          "clip:completed",
          "clip:failed"
        ],
        "title": "SceneStatus",
        "description": "A scene Status record."
      },
      "SchedulerResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "integer",
            "description": "Identifier of the owning user."
          },
          "idea_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the linked content idea."
          },
          "title": {
            "type": [
              "string",
              "null"
            ],
            "description": "Title of the resource."
          },
          "color": {
            "type": [
              "string",
              "null"
            ],
            "description": "Hex color value (e.g. \"#FFFFFF\")."
          },
          "topic": {
            "type": [
              "string",
              "null"
            ],
            "description": "Topic or subject of the content."
          },
          "status": {
            "$ref": "#/components/schemas/SchedulerStatus"
          },
          "type": {
            "type": "string",
            "description": "Type/category discriminator for the resource."
          },
          "source": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/SchedulerSource"
              },
              {
                "type": "null"
              }
            ],
            "description": "Source/origin of the resource."
          },
          "options": {
            "type": [
              "string",
              "null"
            ],
            "description": "Additional generation options for the faceless video."
          },
          "details": {
            "anyOf": [
              {
                "type": "object",
                "properties": {
                  "hours": {
                    "type": "array",
                    "items": {},
                    "description": "Number of hours in the period."
                  },
                  "days": {
                    "type": "integer",
                    "description": "Number of days in the period."
                  },
                  "occurrences": {
                    "type": "array",
                    "items": {},
                    "description": "Number of times the event occurred."
                  },
                  "times_per_day": {
                    "type": "integer",
                    "description": "Number of scheduled occurrences per day."
                  },
                  "start_date": {
                    "description": "ISO-8601 start date of the period."
                  },
                  "weekdays": {
                    "description": "Days of the week the schedule runs on."
                  }
                },
                "required": [
                  "hours",
                  "days",
                  "occurrences",
                  "times_per_day",
                  "start_date",
                  "weekdays"
                ]
              },
              {
                "type": "array",
                "items": {
                  "type": "string"
                },
                "minItems": 0,
                "maxItems": 0,
                "additionalItems": false
              }
            ],
            "description": "Detailed breakdown for the resource."
          },
          "character_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the consistent character (see faceless options)."
          },
          "metadata": {
            "type": "object",
            "properties": {
              "ai_labels": {
                "description": "Whether AI-content disclosure labels are applied on publish."
              },
              "custom_description": {
                "description": "Custom caption/description applied to published posts."
              }
            },
            "required": [
              "ai_labels",
              "custom_description"
            ],
            "description": "Additional metadata for the resource."
          },
          "paused_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was paused, or null."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          },
          "voice": {
            "$ref": "#/components/schemas/VoiceResource"
          },
          "music": {
            "$ref": "#/components/schemas/MediaResource"
          },
          "character": {
            "$ref": "#/components/schemas/CharacterResource"
          },
          "events": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/EventResource"
            },
            "description": "List of related events."
          },
          "videos": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/VideoResource"
            },
            "description": "Videos associated with the resource."
          },
          "social_channels": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SocialChannelResource"
            },
            "description": "Connected social channels for the account."
          },
          "occurrences": {
            "type": "object",
            "description": "Number of times the event occurred."
          }
        },
        "required": [
          "id",
          "user_id",
          "idea_id",
          "title",
          "color",
          "topic",
          "status",
          "type",
          "source",
          "options",
          "details",
          "character_id",
          "metadata",
          "paused_at",
          "created_at",
          "updated_at"
        ],
        "title": "SchedulerResource",
        "description": "A scheduler record."
      },
      "SchedulerSource": {
        "type": "string",
        "enum": [
          "ai",
          "csv",
          "manual"
        ],
        "title": "SchedulerSource",
        "description": "A scheduler Source record."
      },
      "SchedulerStatus": {
        "type": "string",
        "enum": [
          "draft",
          "failed",
          "paused",
          "writing",
          "deleted",
          "completed",
          "reviewing",
          "scheduled",
          "publishing",
          "generating"
        ],
        "title": "SchedulerStatus",
        "description": "A scheduler Status record."
      },
      "SocialAccountEnum": {
        "type": "integer",
        "enum": [
          0,
          1,
          2,
          3,
          4,
          5,
          6,
          7
        ],
        "title": "SocialAccountEnum",
        "description": "A social Account Enum record."
      },
      "SocialChannelResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "provider": {
            "type": "string",
            "description": "Upstream provider that fulfilled the resource."
          },
          "provider_id": {
            "type": [
              "string",
              "null"
            ],
            "description": "Provider-side identifier for the resource."
          },
          "name": {
            "type": [
              "string",
              "null"
            ],
            "description": "Display name of the resource."
          },
          "avatar": {
            "type": [
              "string",
              "null"
            ],
            "description": "URL of the user's avatar image, if set."
          },
          "type": {
            "type": "string",
            "description": "Type/category discriminator for the resource."
          },
          "icon": {
            "type": "string",
            "description": "Icon URL or identifier for the resource."
          },
          "needs_reauth": {
            "type": "boolean",
            "description": "Whether the connected account must be re-authenticated."
          },
          "expires_in": {
            "type": "integer",
            "const": 94608000,
            "description": "Seconds until the resource expires."
          },
          "errors": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Map of field name to validation error messages."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "provider",
          "provider_id",
          "name",
          "avatar",
          "type",
          "icon",
          "needs_reauth",
          "expires_in",
          "errors",
          "created_at",
          "updated_at"
        ],
        "title": "SocialChannelResource",
        "description": "A social Channel record."
      },
      "StoryboardResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "uuid": {
            "type": "string",
            "description": "Globally unique UUID for the resource."
          },
          "user_id": {
            "type": "integer",
            "description": "Identifier of the owning user."
          },
          "user": {
            "$ref": "#/components/schemas/UserResource"
          },
          "status": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/StoryboardStatus"
              },
              {
                "type": "null"
              }
            ],
            "description": "Current lifecycle status of the resource."
          },
          "is_locked": {
            "type": "boolean",
            "description": "Whether the record is locked from editing."
          },
          "prompt": {
            "type": [
              "string",
              "null"
            ],
            "description": "Generation prompt text."
          },
          "duration": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Target video length in seconds."
          },
          "settings": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Configuration settings for the resource."
          },
          "video_id": {
            "type": "integer",
            "description": "Identifier of the parent video."
          },
          "video": {
            "$ref": "#/components/schemas/VideoResource"
          },
          "clip_engine_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the text-to-video (clip) engine (see faceless options)."
          },
          "clip_engine": {
            "$ref": "#/components/schemas/EngineResource"
          },
          "image_engine_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the text-to-image engine (see faceless options)."
          },
          "image_engine": {
            "$ref": "#/components/schemas/EngineResource"
          },
          "scenes": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SceneResource"
            },
            "description": "Ordered scenes that compose the video."
          },
          "media": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/MediaResource"
            },
            "description": "Underlying media files attached to the resource."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "uuid",
          "user_id",
          "status",
          "is_locked",
          "prompt",
          "duration",
          "settings",
          "video_id",
          "clip_engine_id",
          "image_engine_id",
          "created_at",
          "updated_at"
        ],
        "title": "StoryboardResource",
        "description": "A storyboard record."
      },
      "StoryboardStatus": {
        "type": "string",
        "enum": [
          "wizard",
          "processing",
          "generating:prompts",
          "generating:subjects",
          "generating:hero",
          "generating:frames",
          "formatting:prompts",
          "ready",
          "failed"
        ],
        "title": "StoryboardStatus",
        "description": "A storyboard Status record."
      },
      "SubscriptionProvider": {
        "type": "integer",
        "enum": [
          1,
          2,
          3,
          4
        ],
        "title": "SubscriptionProvider",
        "description": "A subscription Provider record."
      },
      "SurveyAnswerResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "answer": {
            "type": [
              "string",
              "null"
            ],
            "description": "The answer text submitted for the survey question."
          },
          "type": {
            "type": "string",
            "description": "Type/category discriminator for the resource."
          },
          "created_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "answer",
          "type",
          "created_at",
          "updated_at"
        ],
        "title": "SurveyAnswerResource",
        "description": "A survey Answer record."
      },
      "TagResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the owning user."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "slug": {
            "type": "string",
            "description": "URL-friendly unique identifier for the resource."
          },
          "color": {
            "type": [
              "string",
              "null"
            ],
            "description": "Hex color value (e.g. \"#FFFFFF\")."
          },
          "user": {
            "$ref": "#/components/schemas/UserResource"
          },
          "templates": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TemplateResource"
            },
            "description": "Templates associated with the resource."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "name",
          "slug",
          "color",
          "created_at",
          "updated_at"
        ],
        "title": "TagResource",
        "description": "A tag record."
      },
      "TemplateResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "string",
            "description": "Identifier of the owning user."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "slug": {
            "type": "string",
            "description": "URL-friendly unique identifier for the resource."
          },
          "description": {
            "type": "string",
            "description": "Human-readable description of the resource."
          },
          "type": {
            "type": "string",
            "description": "Type/category discriminator for the resource."
          },
          "metadata": {
            "type": "string",
            "description": "Additional metadata for the resource."
          },
          "source": {
            "type": "string",
            "description": "Source/origin of the resource."
          },
          "is_active": {
            "type": "string",
            "description": "Whether the record is active."
          },
          "user": {
            "$ref": "#/components/schemas/UserResource"
          },
          "tags": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/TagResource"
            },
            "description": "Tags associated with the resource."
          },
          "media": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/MediaResource"
            },
            "description": "Underlying media files attached to the resource."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "name",
          "slug",
          "description",
          "type",
          "metadata",
          "source",
          "is_active",
          "created_at",
          "updated_at"
        ],
        "title": "TemplateResource",
        "description": "A template record."
      },
      "TrackerResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the owning user."
          },
          "trackable_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the tracked entity."
          },
          "trackable_type": {
            "type": [
              "string",
              "null"
            ],
            "description": "Class/type of the tracked entity."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "count": {
            "type": "integer",
            "description": "Count value for the metric."
          },
          "limit": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Maximum number of items returned."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "trackable_id",
          "trackable_type",
          "name",
          "count",
          "limit",
          "created_at",
          "updated_at"
        ],
        "title": "TrackerResource",
        "description": "A tracker record."
      },
      "UpdateFacelessRequest": {
        "type": "object",
        "description": "v2 public-API input contract for updating a faceless video.\nInherits v1 rules; override here when the public contract must diverge.",
        "properties": {
          "voice_id": {
            "type": "integer",
            "description": "Optional — identifier of the narration voice (see faceless options). Omit voice entirely to render without narration."
          },
          "background_id": {
            "type": "integer",
            "description": "Optional — identifier of the background asset (see faceless options)."
          },
          "music_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Optional — identifier of the background music track (media id), or null to remove music."
          },
          "genre_id": {
            "type": "integer",
            "description": "Optional — identifier of the genre/style (see faceless options). Required at render time for the `ai-visuals` and `ai-clips` types."
          },
          "image_engine_id": {
            "type": "integer",
            "description": "Optional — identifier of the text-to-image engine (see faceless options). Relevant only for the `ai-visuals` and `ai-clips` types."
          },
          "clip_engine_id": {
            "type": "integer",
            "description": "Optional — identifier of the text-to-video (clip) engine (see faceless options). Relevant only for clip-based types."
          },
          "transition": {
            "type": [
              "string",
              "null"
            ],
            "description": "Optional — transition slug applied between scenes (see faceless options).",
            "enum": [
              "slide-left",
              "slide-right",
              "slide-up",
              "slide-down",
              "scale-in",
              "scale-out",
              "zoom-in",
              "zoom-out",
              "rotate-left",
              "rotate-right",
              "fade",
              "none",
              "mixed",
              "pop",
              "dreamy",
              "swing",
              "spin-right",
              "spin-left",
              "swoosh-left",
              "swoosh-right",
              "glide-left",
              "glide-right",
              "drop",
              "tumble-left",
              "tumble-right",
              "float",
              "rise-left",
              "rise-right",
              "bounce",
              "flash",
              "crossfade",
              "blur-dissolve",
              "zoom-dissolve"
            ]
          },
          "animation": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "pan-in",
              "pan-out",
              "pan-left",
              "pan-right",
              "pan-up",
              "pan-down",
              "rotate-left-in",
              "rotate-right-in",
              "float",
              "none",
              "mixed"
            ],
            "description": "Optional — per-image motion effect slug (e.g. \"pan-in\"). See faceless options."
          },
          "sfx": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "none",
              "whoosh"
            ],
            "description": "Optional — sound-effect slug applied to the video (see faceless options)."
          },
          "volume": {
            "type": [
              "string",
              "null"
            ],
            "enum": [
              "low",
              "medium",
              "high"
            ],
            "description": "Optional — background-music volume level: \"low\", \"medium\", or \"high\"."
          },
          "script": {
            "type": "string",
            "description": "Optional — supply a full custom script to use verbatim instead of generating one. Provide this via PATCH /faceless/{faceless}; the script-generation step is then unnecessary."
          },
          "duration": {
            "type": "integer",
            "description": "Optional — target video length in seconds. Any positive integer; not restricted to the script-generation presets (those fixed values apply only to PUT /faceless/{faceless}/scripts)."
          },
          "aspect_ratio": {
            "type": "string",
            "enum": [
              "16:9",
              "9:16",
              "1:1"
            ],
            "description": "Optional — output aspect ratio: \"16:9\", \"9:16\", or \"1:1\"."
          },
          "captions": {
            "type": "object",
            "properties": {
              "font_family": {
                "type": "string",
                "description": "Caption font family slug (see faceless options)."
              },
              "font_color": {
                "type": "string",
                "description": "Caption font color as a hex value (e.g. \"#FFFFFF\")."
              },
              "font_url": {
                "type": [
                  "string",
                  "null"
                ],
                "format": "uri",
                "description": "URL of a custom font file to use for captions."
              },
              "position": {
                "type": "string",
                "enum": [
                  "top",
                  "bottom",
                  "center"
                ],
                "description": "On-screen position slug (e.g. \"bottom\", \"center\", \"top\")."
              }
            },
            "description": "Optional — caption styling. Only `font_family`, `font_color`, `font_url`, and `position` are honored on update; any other caption keys are ignored."
          }
        },
        "title": "UpdateFacelessRequest"
      },
      "User": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "email": {
            "type": "string",
            "description": "The user's email address."
          },
          "provider_id": {
            "type": [
              "string",
              "null"
            ],
            "description": "Provider-side identifier for the resource."
          },
          "provider": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/SocialAccountEnum"
              },
              {
                "type": "null"
              }
            ],
            "description": "Upstream provider that fulfilled the resource."
          },
          "active": {
            "type": "boolean",
            "description": "Whether the record is currently active and selectable."
          },
          "is_active": {
            "type": "integer",
            "description": "Whether the record is active."
          },
          "registration_code": {
            "type": [
              "string",
              "null"
            ],
            "description": "Code used during account registration, if any."
          },
          "promo_code": {
            "type": [
              "string",
              "null"
            ],
            "description": "Promotional code applied to the account."
          },
          "settings": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Configuration settings for the resource."
          },
          "notifications": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Notification preferences for the user."
          },
          "ad_tracking": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Whether ad/conversion tracking is enabled for this user."
          },
          "mailing_list": {
            "type": "integer",
            "description": "Whether the user opted into the marketing mailing list."
          },
          "email_verified_at": {
            "type": [
              "string",
              "null"
            ],
            "description": "ISO-8601 timestamp when the email was verified, or null."
          },
          "user_type": {
            "$ref": "#/components/schemas/UserType"
          },
          "locale": {
            "type": [
              "string",
              "null"
            ],
            "description": "BCP-47 locale code (e.g. \"en-US\")."
          },
          "timezone": {
            "type": [
              "string",
              "null"
            ],
            "description": "IANA timezone name (e.g. \"America/New_York\")."
          },
          "plan_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the subscription plan."
          },
          "subscription_ends_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp the subscription ends/renews, or null."
          },
          "trial_ends_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp the trial ends, or null."
          },
          "pm_last_four": {
            "type": [
              "string",
              "null"
            ],
            "description": "Last four digits of the saved payment method."
          },
          "pm_type": {
            "type": [
              "string",
              "null"
            ],
            "description": "Saved payment-method type (e.g. \"visa\", \"mastercard\")."
          },
          "pm_exemption_code": {
            "type": [
              "string",
              "null"
            ],
            "description": "Tax/payment-method exemption code, if applicable."
          },
          "stripe_id": {
            "type": [
              "string",
              "null"
            ],
            "description": "Stripe customer identifier (Stripe-billed users only)."
          },
          "apple_account_token": {
            "type": [
              "string",
              "null"
            ],
            "description": "Opaque Apple App Store account token (Apple IAP users only)."
          },
          "subscription_provider": {
            "$ref": "#/components/schemas/SubscriptionProvider"
          },
          "signup_platform": {
            "type": [
              "string",
              "null"
            ],
            "description": "Platform the user signed up from (e.g. \"web\", \"ios\")."
          },
          "is_lifetime": {
            "type": "boolean",
            "description": "Whether the plan is a lifetime (non-recurring) deal."
          },
          "created_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": [
              "string",
              "null"
            ],
            "format": "date-time",
            "description": "ISO-8601 timestamp when the record was last updated."
          },
          "remaining_credit_amount": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Remaining monthly credits available to spend."
          },
          "monthly_credit_amount": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Monthly credit allotment granted by the plan."
          },
          "extra_credits": {
            "type": "integer",
            "description": "Extra (top-up) credits available beyond the monthly allotment."
          }
        },
        "required": [
          "id",
          "name",
          "email",
          "provider_id",
          "provider",
          "active",
          "is_active",
          "registration_code",
          "promo_code",
          "settings",
          "notifications",
          "ad_tracking",
          "mailing_list",
          "email_verified_at",
          "user_type",
          "locale",
          "timezone",
          "plan_id",
          "subscription_ends_at",
          "trial_ends_at",
          "pm_last_four",
          "pm_type",
          "pm_exemption_code",
          "stripe_id",
          "apple_account_token",
          "subscription_provider",
          "signup_platform",
          "is_lifetime",
          "created_at",
          "updated_at",
          "remaining_credit_amount",
          "monthly_credit_amount",
          "extra_credits"
        ],
        "title": "User",
        "description": "A user record."
      },
      "UserResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "name": {
            "type": "string",
            "description": "Display name of the resource."
          },
          "stripe_id": {
            "type": [
              "string",
              "null"
            ],
            "description": "Stripe customer identifier (Stripe-billed users only)."
          },
          "email": {
            "type": "string",
            "description": "The user's email address."
          },
          "email_verified": {
            "type": "boolean",
            "description": "Whether the user has verified their email address."
          },
          "credits": {
            "type": "object",
            "properties": {
              "remaining": {
                "type": "integer",
                "description": "Remaining monthly credits available to spend."
              },
              "total": {
                "type": "integer",
                "description": "Total monthly credit allotment."
              },
              "extra": {
                "type": "integer",
                "description": "Extra (top-up) credits available beyond the monthly allotment."
              }
            },
            "required": [
              "remaining",
              "total",
              "extra"
            ],
            "description": "Credit balance summary for the user."
          },
          "subscription": {
            "anyOf": [
              {
                "type": "object",
                "properties": {
                  "exists": {
                    "type": "boolean",
                    "description": "Whether a subscription exists for the user."
                  },
                  "trial": {
                    "type": "string",
                    "description": "Whether the subscription is currently in a trial period."
                  },
                  "active": {
                    "type": "string",
                    "description": "Whether the record is currently active and selectable."
                  },
                  "is_lifetime": {
                    "type": "boolean",
                    "description": "Whether the plan is a lifetime (non-recurring) deal."
                  },
                  "plan_id": {
                    "type": [
                      "integer",
                      "null"
                    ],
                    "description": "Identifier of the subscription plan."
                  },
                  "recurring": {
                    "type": "string",
                    "description": "Whether the subscription/charge recurs."
                  },
                  "subscription_status": {
                    "type": "string",
                    "description": "Current subscription status (e.g. \"active\", \"trialing\")."
                  },
                  "ends_at": {
                    "type": "string",
                    "description": "ISO-8601 timestamp marking the end of the period."
                  },
                  "purchase_token": {
                    "type": [
                      "string",
                      "null"
                    ],
                    "description": "Google Play purchase token (Play Billing users only)."
                  },
                  "expires_at": {
                    "type": "string",
                    "description": "ISO-8601 timestamp when the resource expires, or null."
                  },
                  "original_transaction_id": {
                    "type": [
                      "string",
                      "null"
                    ],
                    "description": "Original store transaction identifier (IAP users only)."
                  },
                  "auto_renewing": {
                    "type": "string",
                    "description": "Whether the store subscription is set to auto-renew."
                  }
                },
                "required": [
                  "exists",
                  "trial",
                  "active",
                  "is_lifetime",
                  "plan_id",
                  "recurring",
                  "subscription_status",
                  "ends_at",
                  "purchase_token",
                  "expires_at",
                  "original_transaction_id",
                  "auto_renewing"
                ]
              },
              {
                "type": "object",
                "properties": {
                  "exists": {
                    "type": "boolean",
                    "description": "Whether a subscription exists for the user."
                  },
                  "trial": {
                    "type": "boolean",
                    "description": "Whether the subscription is currently in a trial period."
                  },
                  "active": {
                    "type": "boolean",
                    "description": "Whether the record is currently active and selectable."
                  },
                  "is_lifetime": {
                    "type": "boolean",
                    "description": "Whether the plan is a lifetime (non-recurring) deal."
                  }
                },
                "required": [
                  "exists",
                  "trial",
                  "active",
                  "is_lifetime"
                ]
              }
            ],
            "description": "High-level subscription state for the user."
          },
          "settings": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Configuration settings for the resource."
          },
          "notifications": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Notification preferences for the user."
          },
          "features": {
            "type": "array",
            "items": {},
            "description": "Feature flags or entitlements enabled for the plan."
          },
          "source": {
            "type": "string",
            "description": "Source/origin of the resource."
          },
          "apple_account_token": {
            "type": "string",
            "description": "Opaque Apple App Store account token (Apple IAP users only)."
          },
          "hide_real_clone": {
            "type": "boolean",
            "description": "Whether to hide the user's real cloned voice from listings."
          },
          "onboarding": {
            "type": "object",
            "properties": {
              "video_id": {
                "type": "string",
                "description": "Identifier of the parent video."
              },
              "status": {
                "type": "string",
                "description": "Current lifecycle status of the resource."
              },
              "faceless_id": {
                "type": "string",
                "description": "Identifier of the parent faceless video."
              }
            },
            "required": [
              "video_id",
              "status",
              "faceless_id"
            ],
            "description": "Onboarding progress/state for the user."
          },
          "answers": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/SurveyAnswerResource"
            },
            "description": "Collection of submitted survey answers."
          },
          "show_welcome_modal": {
            "type": "string",
            "description": "Whether the welcome modal should be shown to the user."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "name",
          "stripe_id",
          "email",
          "email_verified",
          "credits",
          "subscription",
          "settings",
          "notifications",
          "features",
          "source",
          "hide_real_clone",
          "show_welcome_modal",
          "created_at",
          "updated_at"
        ],
        "title": "UserResource",
        "description": "A user record."
      },
      "UserType": {
        "type": "integer",
        "enum": [
          1,
          2,
          3,
          4
        ],
        "title": "UserType",
        "description": "A user Type record."
      },
      "VideoResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": "integer",
            "description": "Identifier of the owning user."
          },
          "idea_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the linked content idea."
          },
          "scheduler_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the owning scheduler."
          },
          "title": {
            "type": [
              "string",
              "null"
            ],
            "description": "Title of the resource."
          },
          "type": {
            "type": [
              "string",
              "null"
            ],
            "description": "Type/category discriminator for the resource."
          },
          "url": {
            "type": [
              "string",
              "null"
            ],
            "description": "Playable URL of the rendered video (mp4). Populated once the render completes (status `completed`); null while drafting/rendering or if the render failed."
          },
          "status": {
            "anyOf": [
              {
                "$ref": "#/components/schemas/VideoStatus"
              },
              {
                "type": "null"
              }
            ],
            "description": "Current lifecycle status of the resource."
          },
          "retries": {
            "type": "integer",
            "description": "Number of times processing has been retried."
          },
          "hash": {
            "type": [
              "string",
              "null"
            ],
            "description": "Opaque content hash used for change detection."
          },
          "synced_at": {
            "type": "string",
            "description": "ISO-8601 timestamp the resource was last synced, or null."
          },
          "metadata": {
            "type": "object",
            "properties": {
              "ai_labels": {
                "description": "Whether AI-content disclosure labels are applied on publish."
              },
              "custom_description": {
                "description": "Custom caption/description applied to published posts."
              }
            },
            "required": [
              "ai_labels",
              "custom_description"
            ],
            "description": "Additional metadata for the resource."
          },
          "failure": {
            "type": [
              "object",
              "null"
            ],
            "nullable": true,
            "description": "Present only when status is \"failed\": the categorized reason the render failed; null otherwise.",
            "properties": {
              "code": {
                "type": "string",
                "description": "Stable machine-readable failure category the client can branch on.",
                "enum": [
                  "voiceover_failed",
                  "script_processing_failed",
                  "stock_footage_failed",
                  "asset_generation_failed",
                  "image_generation_failed",
                  "composition_failed",
                  "music_failed",
                  "watermark_failed",
                  "background_failed",
                  "source_build_failed",
                  "charge_failed",
                  "render_failed"
                ]
              },
              "message": {
                "type": "string",
                "description": "Human-readable, safe failure message suitable for display to end users."
              }
            }
          },
          "user": {
            "$ref": "#/components/schemas/UserResource"
          },
          "media": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/MediaResource"
            },
            "description": "Underlying media files attached to the resource."
          },
          "idea": {
            "$ref": "#/components/schemas/IdeaResource"
          },
          "faceless": {
            "$ref": "#/components/schemas/App.Http.Resources.FacelessResource"
          },
          "storyboard": {
            "$ref": "#/components/schemas/StoryboardResource"
          },
          "resource": {
            "$ref": "#/components/schemas/FolderWithContentResource"
          },
          "publications": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/PublicationResource"
            },
            "description": "Scheduled or published social posts for this video."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "idea_id",
          "scheduler_id",
          "title",
          "type",
          "url",
          "status",
          "retries",
          "hash",
          "synced_at",
          "metadata",
          "created_at",
          "updated_at"
        ],
        "title": "VideoResource",
        "description": "A video record.",
        "example": {
          "id": 10,
          "user_id": 1,
          "idea_id": null,
          "scheduler_id": null,
          "title": "My faceless video",
          "type": "faceless",
          "url": null,
          "status": "failed",
          "retries": 1,
          "hash": "abc123",
          "synced_at": null,
          "metadata": {
            "ai_labels": true,
            "custom_description": null
          },
          "failure": {
            "code": "voiceover_failed",
            "message": "Voiceover generation failed. Please try again shortly or contact support if it persists."
          },
          "created_at": "2026-01-01T12:00:00.000000Z",
          "updated_at": "2026-01-01T12:00:00.000000Z"
        }
      },
      "VideoStatus": {
        "type": "string",
        "enum": [
          "draft",
          "failed",
          "syncing",
          "rendering",
          "completed",
          "sync-failed",
          "timeout",
          "modifying",
          "modified"
        ],
        "title": "VideoStatus",
        "description": "A video Status record."
      },
      "VoiceResource": {
        "type": "object",
        "properties": {
          "id": {
            "type": "integer",
            "description": "Unique numeric identifier of the resource."
          },
          "user_id": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Identifier of the owning user."
          },
          "name": {
            "type": [
              "string",
              "null"
            ],
            "description": "Display name of the resource."
          },
          "preview": {
            "type": [
              "string",
              "null"
            ],
            "description": "URL of a preview image or clip for the resource."
          },
          "language": {
            "type": [
              "string",
              "null"
            ],
            "description": "Language of the content (e.g. \"english\")."
          },
          "accent": {
            "type": [
              "string",
              "null"
            ],
            "description": "Accent of the voice (e.g. \"american\", \"british\")."
          },
          "gender": {
            "type": [
              "string",
              "null"
            ],
            "description": "Gender label (e.g. \"male\", \"female\", \"neutral\")."
          },
          "provider": {
            "type": [
              "string",
              "null"
            ],
            "description": "Upstream provider that fulfilled the resource."
          },
          "provider_id": {
            "type": [
              "string",
              "null"
            ],
            "description": "Provider-side identifier for the resource."
          },
          "words_per_minute": {
            "type": "integer",
            "description": "The words per minute value for the resource."
          },
          "type": {
            "type": [
              "string",
              "null"
            ],
            "description": "Type/category discriminator for the resource."
          },
          "is_active": {
            "type": "boolean",
            "description": "Whether the record is active."
          },
          "metadata": {
            "type": [
              "array",
              "null"
            ],
            "items": {},
            "description": "Additional metadata for the resource."
          },
          "order": {
            "type": [
              "integer",
              "null"
            ],
            "description": "Zero-based ordering position within its collection."
          },
          "created_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was created."
          },
          "updated_at": {
            "type": "string",
            "description": "ISO-8601 timestamp when the record was last updated."
          }
        },
        "required": [
          "id",
          "user_id",
          "name",
          "preview",
          "language",
          "accent",
          "gender",
          "provider",
          "provider_id",
          "words_per_minute",
          "type",
          "is_active",
          "metadata",
          "order",
          "created_at",
          "updated_at"
        ],
        "title": "VoiceResource",
        "description": "A voice record."
      },
      "ScrapeImagesRequest": {
        "type": "object",
        "properties": {
          "url": {
            "type": "string",
            "format": "uri",
            "description": "Publicly reachable web page URL to extract product/page images from. Social-media URLs (YouTube, TikTok, Twitter/X, Instagram, Facebook, etc.) are rejected with `422`."
          }
        },
        "required": [
          "url"
        ],
        "title": "ScrapeImagesRequest",
        "description": "A scrape Images Request record."
      },
      "ScrapeScriptRequest": {
        "type": "object",
        "properties": {
          "url": {
            "type": "string",
            "format": "uri",
            "description": "Publicly reachable web page URL to extract script content from. Social-media URLs are rejected with `422`."
          },
          "duration": {
            "type": "integer",
            "enum": [
              30,
              60,
              180,
              300,
              600,
              900
            ],
            "description": "Target length of the generated script in seconds. Must be one of 30, 60, 180, 300, 600, or 900."
          },
          "style": {
            "type": "string",
            "description": "Narrative style for the generated script (free-form text, max 255 chars). Examples: educational, storytelling, listicle, conversational, motivational."
          },
          "language": {
            "type": "string",
            "description": "Language for the generated script (e.g. \"english\")."
          },
          "tone": {
            "type": "string",
            "description": "Tone of voice for the generated script. Examples: professional, friendly, casual, authoritative."
          }
        },
        "required": [
          "url",
          "duration",
          "style",
          "language",
          "tone"
        ],
        "title": "ScrapeScriptRequest",
        "description": "A scrape Script Request record."
      }
    },
    "responses": {
      "AuthenticationException": {
        "description": "Unauthenticated",
        "content": {
          "application/json": {
            "schema": {
              "type": "object",
              "properties": {
                "message": {
                  "type": "string",
                  "description": "Error overview."
                }
              },
              "required": [
                "message"
              ]
            },
            "example": {
              "message": "Unauthenticated."
            }
          }
        }
      },
      "ValidationException": {
        "description": "Validation error",
        "content": {
          "application/json": {
            "schema": {
              "type": "object",
              "properties": {
                "message": {
                  "type": "string",
                  "description": "Errors overview."
                },
                "errors": {
                  "type": "object",
                  "description": "A detailed description of each field that failed validation.",
                  "additionalProperties": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    }
                  }
                }
              },
              "required": [
                "message",
                "errors"
              ]
            },
            "example": {
              "message": "The given data was invalid.",
              "errors": {
                "voice_id": [
                  "The selected voice id is invalid."
                ]
              }
            }
          }
        }
      },
      "AuthorizationException": {
        "description": "Authorization error",
        "content": {
          "application/json": {
            "schema": {
              "type": "object",
              "properties": {
                "message": {
                  "type": "string",
                  "description": "Error overview."
                }
              },
              "required": [
                "message"
              ]
            },
            "example": {
              "message": "This action is unauthorized."
            }
          }
        }
      },
      "ModelNotFoundException": {
        "description": "Not found",
        "content": {
          "application/json": {
            "schema": {
              "type": "object",
              "properties": {
                "message": {
                  "type": "string",
                  "description": "Error overview."
                }
              },
              "required": [
                "message"
              ]
            },
            "example": {
              "message": "No query results for the requested resource."
            }
          }
        }
      },
      "TooManyRequests": {
        "description": "Rate limit exceeded — requests are limited per API token (30 per minute by default). The response carries `Retry-After` (seconds to wait) and `X-RateLimit-Reset` (Unix timestamp when the window resets); back off until then and retry. Successful responses include `X-RateLimit-Limit` and `X-RateLimit-Remaining` so you can pace requests proactively.",
        "content": {
          "application/json": {
            "example": {
              "message": "Too Many Attempts."
            }
          }
        }
      },
      "BadRequest": {
        "description": "Bad request — e.g. an `include` value outside the endpoint's allowlist.",
        "content": {
          "application/json": {
            "schema": {
              "type": "object",
              "properties": {
                "message": {
                  "type": "string",
                  "description": "Error overview."
                }
              },
              "required": [
                "message"
              ]
            },
            "example": {
              "message": "Requested include(s) `foo` are not allowed. Allowed include(s) are `video, captions, media, music, voice, background, genre, watermark, character, assets`."
            }
          }
        }
      },
      "PaymentRequired": {
        "description": "Insufficient credits. The request is authenticated and valid, but the account balance is too low — top up and retry.",
        "content": {
          "application/json": {
            "schema": {
              "type": "object",
              "properties": {
                "message": {
                  "type": "string",
                  "example": "You do not have enough credits to render this video"
                },
                "status": {
                  "type": "integer",
                  "example": 402
                },
                "error": {
                  "type": "object",
                  "properties": {
                    "code": {
                      "type": "string",
                      "example": "INSUFFICIENT-CREDITS"
                    },
                    "status": {
                      "type": "integer",
                      "example": 402
                    },
                    "required": {
                      "type": "integer",
                      "example": 13
                    },
                    "available": {
                      "type": "integer",
                      "example": 4
                    }
                  }
                }
              }
            }
          }
        }
      },
      "SubscriptionRequired": {
        "description": "No active subscription. The v2 public API has no free tier — every faceless and preset endpoint (reads included) requires an active subscription. Unsubscribed, expired, or canceled callers are rejected with this `403` (code `SUBSCRIPTION-REQUIRED`) before any ownership, credit, or validation check. Only `GET /me`, `GET /credits/costs`, and `GET /credits/history` are reachable without one.",
        "content": {
          "application/json": {
            "schema": {
              "type": "object",
              "properties": {
                "message": {
                  "type": "string",
                  "description": "Human-readable status message for the response.",
                  "example": "An active subscription is required."
                },
                "error": {
                  "type": "object",
                  "description": "Structured error detail.",
                  "properties": {
                    "code": {
                      "type": "string",
                      "description": "Stable machine-readable error code — `SUBSCRIPTION-REQUIRED` here.",
                      "example": "SUBSCRIPTION-REQUIRED"
                    },
                    "status": {
                      "type": "integer",
                      "description": "HTTP status code echoed in the error body.",
                      "example": 403
                    }
                  }
                }
              }
            },
            "example": {
              "message": "An active subscription is required.",
              "error": {
                "code": "SUBSCRIPTION-REQUIRED",
                "status": 403
              }
            }
          }
        }
      },
      "SubscriptionRequiredOrAuthorization": {
        "description": "Forbidden — two distinct causes share this status:\n\n1. **No active subscription** (code `SUBSCRIPTION-REQUIRED`, message \"An active subscription is required.\") — checked first by the active-subscription gate, before any ownership or precondition logic. The v2 public API has no free tier.\n2. **Authorization / ownership or precondition failure** — the subscription is active but the action is not allowed: the resource belongs to another account, or a render precondition is unmet (e.g. `A script is required before rendering.`, `Voice was not provided.`, the video is busy, or storage is full).",
        "content": {
          "application/json": {
            "schema": {
              "type": "object",
              "properties": {
                "message": {
                  "type": "string",
                  "description": "Human-readable status message for the response.",
                  "example": "An active subscription is required."
                },
                "error": {
                  "type": "object",
                  "description": "Structured error detail, present on the gate (`SUBSCRIPTION-REQUIRED`) and code-bearing authorization failures.",
                  "properties": {
                    "code": {
                      "type": "string",
                      "description": "Stable machine-readable error code — `SUBSCRIPTION-REQUIRED` for the subscription gate.",
                      "example": "SUBSCRIPTION-REQUIRED"
                    },
                    "status": {
                      "type": "integer",
                      "description": "HTTP status code echoed in the error body.",
                      "example": 403
                    }
                  }
                }
              }
            },
            "example": {
              "message": "An active subscription is required.",
              "error": {
                "code": "SUBSCRIPTION-REQUIRED",
                "status": 403
              }
            }
          }
        }
      }
    }
  },
  "tags": [
    {
      "name": "Account",
      "description": "The authenticated user — profile, per-feature credit costs, and the credit ledger."
    },
    {
      "name": "Faceless Videos",
      "description": "Create, configure, render, and retrieve faceless videos, their assets, and reusable presets."
    }
  ]
}
