Generation Templates

One-field effects and Compose recipes for AI video. Apply curated effects to normal generations, or plan and render a full short-form production.

Generation Templates includes two related surfaces:

  • Effect templates: pre-curated creative effects for /v1/images/generations and /v1/videos/generations. Pass template: "<slug>" and EmpirioLabs applies the tuned effect to a normal generation request.
  • Compose recipes: full-production short-form video workflows. Compose plans scenes, creates or selects visuals, generates voiceover, captions, optional music, and returns a finished MP4.

The same catalog powers the Templates button in the playground, where Effects and Compose appear as top-level tabs.

List templates

GET
/v1/templates
1curl https://api.empiriolabs.ai/v1/templates \
2 -H "Authorization: Bearer <token>" \
3 -H "Content-Type: application/json"

Use the generic endpoint for the full image and video catalog, or the modality-specific endpoints when you already know the generation type.

$curl https://api.empiriolabs.ai/v1/templates?modality=image \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY"

List video templates

GET
/v1/videos/templates
1curl https://api.empiriolabs.ai/v1/videos/templates \
2 -H "Authorization: Bearer <token>" \
3 -H "Content-Type: application/json"

Filters

  • category: viral, cinematic, motion, transform, social, extend, product, edit, portrait
  • modality: video or image
  • model: only return templates that support a specific model slug
  • featured: true to filter to featured templates only
$curl https://api.empiriolabs.ai/v1/videos/templates?category=viral \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY"

Response shape

1{
2 "object": "list",
3 "template_count": 11,
4 "data": [
5 {
6 "slug": "baseball-stadium",
7 "display_name": "Stadium",
8 "category": "viral",
9 "description": "Customer-facing description shown in the playground card.",
10 "recommended_model": "kling-o3",
11 "supported_models": ["kling-o3"],
12 "default_params": { "aspect_ratio": "16:9", "duration": 10 },
13 "required_inputs": { "image": true, "min_images": 1, "max_images": 1 },
14 "cover_image_url": "https://media.empiriolabs.ai/assets/template-posters/baseball-stadium.jpg",
15 "preview_video_url": "https://media.empiriolabs.ai/assets/template-previews/baseball-stadium.mp4",
16 "modality": "video",
17 "is_featured": true,
18 "display_order": 10
19 }
20 ]
21}

List image templates

GET
/v1/images/templates
1curl https://api.empiriolabs.ai/v1/images/templates \
2 -H "Authorization: Bearer <token>" \
3 -H "Content-Type: application/json"
$curl https://api.empiriolabs.ai/v1/images/templates?model=seedream-5-0-lite \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY"

Compose

Compose is the full-production video workflow. Use it when you want a complete short-form video from a brief, script, product idea, or explainable topic. Use effect templates when you want one curated effect applied to a normal image or video generation request.

List Compose recipes

GET
/v1/videos/compose/recipes
1curl https://api.empiriolabs.ai/v1/videos/compose/recipes
$curl https://api.empiriolabs.ai/v1/videos/compose/recipes

The response includes public recipe metadata:

  • slug: pass this as recipe on POST /v1/videos/compose
  • display_name, category, visual_mode, and audio_mode
  • scene_count, aspect_ratios, and default_caption_style
  • requires_face_image and accepts_product_image
  • models: recommended and allowed model options by stage

Model recommendations are read from the live Compose recipe catalog. If you override a stage model, use a value listed in that recipe’s models.<stage>.options.

Plan a storyboard

Use mode: "plan" to turn a topic or script into an editable storyboard. This is the fastest way to preview structure before spending on a full render.

POST
/v1/videos/compose
1curl -X POST https://api.empiriolabs.ai/v1/videos/compose \
2 -H "Authorization: Bearer <token>" \
3 -H "Content-Type: application/json"
$curl https://api.empiriolabs.ai/v1/videos/compose \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY" \
> -H "Content-Type: application/json" \
> -d '{
> "recipe": "custom",
> "mode": "plan",
> "brief": "Explain why cold plunge clips went viral.",
> "aspect_ratio": "9:16",
> "scene_count": 5,
> "caption_style": "bold-white"
> }'

Compose returns an async job:

1{
2 "job_id": "job_01HV3KABCDE",
3 "status": "processing",
4 "poll_url": "/v1/jobs/job_01HV3KABCDE"
5}

Poll the job:

$curl https://api.empiriolabs.ai/v1/jobs/job_01HV3KABCDE \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY"

When the plan job completes, result contains a storyboard. You can edit that JSON before render.

Render the video

Send the storyboard back with mode: "render".

$curl https://api.empiriolabs.ai/v1/videos/compose \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY" \
> -H "Content-Type: application/json" \
> -d '{
> "recipe": "custom",
> "mode": "render",
> "storyboard": {
> "title": "Why cold plunge clips took over",
> "aspect_ratio": "9:16",
> "caption_style": "bold-white",
> "scenes": [
> {
> "index": 1,
> "narration": "Cold plunges look extreme, but the hook is simple.",
> "visual_prompt": "Fast vertical b-roll of ice, water, and a phone recording setup.",
> "duration_seconds": 4
> }
> ]
> }
> }'

The final job result includes the output URL and Compose metadata. Generated media URLs expire after 7 days, so save anything you need to keep.

Edit a render

Use mode: "edit" when you already have a prior render manifest and want to change selected scenes.

1{
2 "recipe": "custom",
3 "mode": "edit",
4 "manifest": {
5 "video_url": "https://media.empiriolabs.ai/worker-outputs/final.mp4",
6 "scenes": [
7 {
8 "index": 1,
9 "clip_url": "https://media.empiriolabs.ai/worker-outputs/scene-1.mp4"
10 }
11 ]
12 },
13 "edits": [
14 {
15 "scene_index": 1,
16 "instruction": "Make the caption hook shorter and punchier."
17 }
18 ]
19}

Common Compose fields

FieldUse
recipeRequired. Recipe slug from GET /v1/videos/compose/recipes.
modeplan, render, or edit.
briefTopic, idea, or direction for plan mode.
scriptOptional script text for plan mode.
storyboardRequired for render mode. Usually the completed plan result.
manifest and editsRequired for edit mode.
aspect_ratioCommon values include 9:16, 16:9, and 1:1, depending on recipe support.
scene_countRequested scene count for plan mode.
caption_styleCaption style ID from the recipes endpoint.
musicOptional music direction or preset.
voiceOptional voice preset or voice ID.
product_imageOptional product reference image for recipes that accept one.
face_imageOptional face or character reference for recipes that require one.
gameplay_styleOptional gameplay background style when the recipe supports gameplay variants.
model_overridesOptional per-stage model overrides, such as { "visual": "seedance-2-0-pro" }.

Compose usage and billing

Compose records a parent usage row for the production, plus internal model legs for script, voice, visuals, transcription, music, and assembly when those stages run. The parent row is the customer-facing row returned by the Account Usage API.

$curl "https://api.empiriolabs.ai/v1/account/usage?source=compose&limit=20" \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY"

Compose rows use source: "compose" and include structured metadata:

1{
2 "source": "compose",
3 "model": "custom",
4 "endpoint": "/v1/videos/compose",
5 "cost": { "amount": 0.1832, "currency": "USD" },
6 "metadata": {
7 "category": "compose",
8 "compose": {
9 "recipe": "custom",
10 "mode": "render",
11 "phase": "render",
12 "leg_count": 5,
13 "total_cost_usd": 0.1832,
14 "legs": [
15 {
16 "stage": "voice",
17 "model": "inworld-tts-mini",
18 "cost_usd": 0.012
19 }
20 ]
21 }
22 }
23}

Read cost.amount for the final debited amount. Use metadata.compose.legs when you want a breakdown of which model stages contributed.

Fetch a single template

GET
/v1/templates/:slug
1curl https://api.empiriolabs.ai/v1/templates/studio-product-shot \
2 -H "Authorization: Bearer <token>" \
3 -H "Content-Type: application/json"
$curl https://api.empiriolabs.ai/v1/templates/studio-product-shot \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY"

Returns 404 with code: "template_not_found" if the slug doesn’t exist.

Generate a video with a template

Add template: "<slug>" to a normal /v1/videos/generations call. You must provide whatever the template requires (required_inputs), usually a reference image.

$curl https://api.empiriolabs.ai/v1/videos/generations \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY" \
> -H "Content-Type: application/json" \
> -d '{
> "template": "baseball-stadium",
> "image_url": "https://example.com/me.jpg"
> }'

Behavior:

  • Model selection: if you don’t pass model, the template’s recommended_model is used. If you do, most templates validate that it is in supported_models and return 400 template_model_unsupported otherwise. Templates with metadata.force_recommended_model: true are pinned to recommended_model for effect fidelity.
  • Modality check: image templates only apply to /v1/images/generations; video templates only apply to /v1/videos/generations.
  • Prompt blend: your prompt (if any) is combined with the template’s built-in styling so the generated output matches both your request and the effect’s aesthetic. Send a short directional prompt; EmpirioLabs handles the rest.
  • Default params: default_params from the template merge in only for keys you didn’t set explicitly.
  • Required inputs: { "image": true } means the call returns 400 template_missing_image if no image_url / image / images is provided.

Generate an image with a template

$curl https://api.empiriolabs.ai/v1/images/generations \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY" \
> -H "Content-Type: application/json" \
> -d '{
> "template": "background-swap",
> "prompt": "Place this product on a brushed steel studio plinth",
> "image": ["https://example.com/product.jpg"]
> }'

The response is the same async job envelope as a normal video generation:

1{
2 "job_id": "abc123...",
3 "status": "processing",
4 "poll_url": "/v1/jobs/abc123..."
5}

Poll GET /v1/jobs/{job_id} until terminal.

Extend a prior video

/v1/videos/generations also accepts extend_from to continue a previous generation. EmpirioLabs handles the prior-clip wiring for you and uses a sensible continuity prompt unless you provide your own.

$curl https://api.empiriolabs.ai/v1/videos/generations \
> -H "Authorization: Bearer $EMPIRIOLABS_API_KEY" \
> -H "Content-Type: application/json" \
> -d '{
> "extend_from": { "job_id": "<prior_job_id>" }
> }'

You can also pass a direct URL:

1{ "extend_from": { "video_url": "https://media.empiriolabs.ai/..." } }

Extend can compose with templates:

1{
2 "template": "action-hero",
3 "extend_from": { "job_id": "<prior>" }
4}

Extend works on every video model

Pass extend_from with any supported video model. If you omit model, EmpirioLabs picks a sensible default for the extend.

Error codes

HTTPcodemeaning
400template_not_foundthe slug doesn’t match any active template
400template_model_unsupportedthe model you passed isn’t in the template’s supported_models
400template_modality_mismatchthe template modality doesn’t match the generation endpoint
400template_missing_imagethe template requires an image but the body didn’t include one
400template_missing_videothe template requires a reference video but the body didn’t include one
400template_no_modelthe template has no recommended_model and you didn’t pass one
400extend_extraction_failedcouldn’t process the prior video for extend. Try a different model.
400extend_invalid_shapeextend_from was malformed
400extend_no_prior_videothe prior job had no resolvable video URL
404extend_prior_not_foundthe job_id in extend_from was unknown
500extend_frame_upload_failedcouldn’t prepare the prior video for extend. Retry, or try a different model.
400compose_unknown_recipethe recipe slug is not active
400compose_bad_modemode was not plan, render, or edit
400missing_briefplan mode needs brief or script content
400missing_storyboardrender mode needs a storyboard
400missing_manifestedit mode needs a prior render manifest
400no_editsedit mode needs at least one edit instruction
401unauthorizedthe request was missing a valid API key
402insufficient_creditsadd credits before starting the job
504compose_render_timeoutthe render exceeded the production budget. Try fewer or shorter scenes.