Generation Templates

One-field presets for image and video generation. Apply product, edit, viral, cinematic, motion, or transform recipes by passing a template slug.

Templates are pre-curated “creative effect” recipes for /v1/images/generations and /v1/videos/generations. Each template ships a canonical prompt, a recommended model, a list of supported models, default parameters, and required input rules. Pass template: "<slug>" in the request body and EmpirioLabs blends the recipe with whatever else you provide, picks the best supported model for you, and forwards the call to the worker.

The same template catalog powers the Templates button in the playground.

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 Cam",
8 "category": "viral",
9 "description": "A 16:9 KBO-style live broadcast fan cam...",
10 "canonical_prompt": "Use the uploaded image as the character identity only...",
11 "recommended_model": "kling-v3-motion-control",
12 "supported_models": ["kling-v3-motion-control"],
13 "default_params": { "aspect_ratio": "16:9", "duration": 5 },
14 "required_inputs": { "image": true, "min_images": 1, "max_images": 1 },
15 "metadata": { "force_recommended_model": true },
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"

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 canonical prompt. Default blend puts your text first for specificity, the canonical second for style baseline. Per-template prompt_strategy controls this.
  • 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. The prior video is forwarded as a reference_video and EmpirioLabs 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

Two strategies, picked automatically based on the model you choose:

StrategyModelsWhat happens
Native reference videokling-o3, kling-v3-motion-control, seedance-2-0-pro, seedance-2-0-fast, wan-2-6, wan-2-7, happyhorse-1-0The prior video flows in as reference_video and the worker conditions on the full clip.
Last-frame extractionhunyuan-video-1-5, moss-video-and-audio, pixverse-v5, pixverse-v5-6, amazon-nova-reel-1-1, svi-2-0-proThe prior video’s last frame is extracted server-side and fed to the model as image_url, so the new clip starts where the old one ended.

If you don’t pass model, EmpirioLabs defaults to seedance-2-0-pro for 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_failedlast-frame extraction couldn’t decode the prior video. Try a ref-video-capable 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_failedextracted frame couldn’t be staged to media storage. Retry, or use a ref-video-capable model.