REST API Reference

Programmatic access to agent-media video generation. Create videos, manage actors, and monitor usage from any language.

Overview

Base URL

https://agent.media/api/v1

Authentication

All requests require a Bearer token. API keys use the ma_ prefix.

Authorization: Bearer ma_your_api_key_here

Rate Limiting

Rate limit headers are returned on responses:X-RateLimit-Limit,X-RateLimit-Remaining,X-RateLimit-Reset. Exceeding the limit returns HTTP 429 with a Retry-After header.

Error Format

{
  "error": {
    "code": "missing_script",
    "message": "Either script or prompt is required",
    "type": "validation_error"
  }
}

Quickstart

1. Get an API key from the dashboard.

2. Create a video:

curl -X POST https://agent.media/api/v1/videos \
  -H "Authorization: Bearer ma_your_api_key" \
  -H "Content-Type: application/json" \
  -d '{
    "script": "Ever wonder why top founders wake up at 5am? It is not about the alarm clock. It is about the mindset.",
    "actor_slug": "emma",
    "style": "hormozi"
  }'

3. Poll for completion (every 5 seconds):

curl https://agent.media/api/v1/videos/YOUR_JOB_ID \
  -H "Authorization: Bearer ma_your_api_key"

4. When status is completed, the output_url field contains the video URL.


POST/api/v1/videos

Create a video generation job. Credits are deducted immediately.

Core Parameters

ParameterTypeRequiredDefaultDescription
scriptstringYes-Video script text (50-3000 chars). Required unless prompt is provided.
promptstringNo-Text prompt to auto-generate script via GPT-4o. +5 credits. Required unless script is provided.
product_urlstringNo-Product page URL for context when generating scripts.
actor_slugstringNo-Library actor slug for talking heads. Browse with GET /actors.
target_durationnumberNoautoTarget duration in seconds: 5, 10, or 15. Auto-estimated from script length if omitted.
stylestringNohormoziSubtitle style. See Subtitle Styles section.

Advanced Parameters

ParameterTypeRequiredDefaultDescription
tonestringNo-Video tone: energetic, calm, confident, dramatic
voice_speednumberNo-TTS speed multiplier (0.7 - 1.5)
musicstringNo-Background music: chill, energetic, corporate, dramatic, upbeat
ctastringNo-End-screen call-to-action text (max 100 chars)
aspect_ratiostringNo9:16Aspect ratio: 9:16, 16:9, 1:1
templatestringNo-Template: monologue, testimonial, product-review, problem-solution, saas-review, before-after, listicle, product-demo
allow_brollbooleanNofalseEnable AI-generated B-roll cutaways
broll_modelstringNo-B-roll model: kling3, hailuo2, wan21
broll_imagesstring[]No-Image URLs for B-roll (max 10)
product_image_urlstringNo-Product image URL for product-focused videos
dub_languagestringNo-BCP-47 language code for dubbing (e.g. es, fr)
webhook_urlstringNo-URL to receive webhook on completion

Composition Parameters

ParameterTypeRequiredDefaultDescription
composition_modestringNo-Set to "pip" for picture-in-picture layout
pip_optionsobjectNo-PIP config: { position, size, animation, frame_style }
pip_options.positionstringNo-bottom-center, bottom-left, bottom-right
pip_options.sizestringNo-small, medium, large
pip_options.animationstringNo-slide-up, slide-left, slide-right, fade, scale
pip_options.frame_stylestringNo-none, rounded, shadow

Scene Control

ParameterTypeRequiredDefaultDescription
scenesarrayNo-Manual scene definitions (max 30)
scenes[].typestringNo-talking_head or broll
scenes[].textstringYes-Narration text for the scene
scenes[].visual_promptstringNo-Prompt for AI-generated visuals
scenes[].imagestringNo-Image URL for the scene

Validation Rules

  • Request body must not exceed 1 MB.
  • All fields are type-checked: target_duration must be 5, 10, or 15; tone must be one of energetic, calm, confident, dramatic; etc.
  • Word count pacing: natural pace is 2.5 words/sec. Max words per duration: 5s = 12, 10s = 25, 15s = 37. Scripts exceeding 37 words are rejected.
  • If a script is too long for the requested target_duration, the duration is auto-upgraded to the next bucket (e.g. 13 words at 5s upgrades to 10s). A pacing_warning field is included in the response when this happens.

Response (201)

{
  "job_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
  "status": "submitted",
  "estimated_duration": 10,
  "credits_deducted": 300,
  "selected_voice": "cgSgspJ2msm6clMCkdW9",
  "voice_auto_detected": false,
  "word_count": 18,
  "words_per_second": 1.8,
  "max_words": 25
}

When using prompt, the response also includes generated_script. When the duration is auto-upgraded, a pacing_warning string is included explaining the adjustment.

curl example

curl -X POST https://agent.media/api/v1/videos \
  -H "Authorization: Bearer ma_your_api_key" \
  -H "Content-Type: application/json" \
  -d '{
    "script": "Ever wonder why top founders wake up at 5am? It is not about the alarm clock.",
    "actor_slug": "emma",
    "style": "hormozi",
    "target_duration": 10,
    "music": "chill"
  }'

GET/api/v1/videos

List your video generation jobs with optional filtering and pagination.

Query Parameters

ParameterTypeRequiredDefaultDescription
limitnumberNo20Results per page (max 100)
offsetnumberNo0Results to skip for pagination
statusstringNo-Filter: submitted, queued, processing, completed, failed, canceled
sortstringNonewestSort order: newest or oldest

Response (200)

{
  "jobs": [
    {
      "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
      "model_slug": "ugc-basic",
      "operation": "ugc_video",
      "status": "completed",
      "credit_cost": 300,
      "output_url": "https://pub-xxx.r2.dev/videos/a1b2c3d4.mp4",
      "created_at": "2026-03-20T14:30:00.000Z",
      "completed_at": "2026-03-20T14:32:15.000Z"
    }
  ],
  "total": 42
}
curl "https://agent.media/api/v1/videos?limit=10&status=completed" \
  -H "Authorization: Bearer ma_your_api_key"

GET/api/v1/videos/:id

Get the status and details of a single video job. Includes Retry-After header for in-progress jobs.

Path Parameters

ParameterTypeRequiredDefaultDescription
idstringYes-Job ID (UUID) from video creation

Response (200) -- completed

{
  "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
  "status": "completed",
  "output_url": "https://pub-xxx.r2.dev/videos/a1b2c3d4.mp4",
  "credit_cost": 300,
  "created_at": "2026-03-20T14:30:00.000Z",
  "completed_at": "2026-03-20T14:32:15.000Z"
}

Non-terminal statuses include a Retry-After: 5 header. Poll every 5 seconds.

curl https://agent.media/api/v1/videos/a1b2c3d4-e5f6-7890-abcd-ef1234567890 \
  -H "Authorization: Bearer ma_your_api_key"

DELETE/api/v1/videos/:id

Soft-delete a video job. The video can be restored later.

Response (200)

{
  "success": true,
  "jobId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
  "deletedAt": "2026-03-20T15:00:00.000Z"
}
curl -X DELETE https://agent.media/api/v1/videos/a1b2c3d4-e5f6-7890-abcd-ef1234567890 \
  -H "Authorization: Bearer ma_your_api_key"

POST/api/v1/videos/:id/cancel

Cancel an in-progress job. Only works for submitted, queued, or processing jobs. Credits are refunded.

Response (200)

{
  "canceled": true,
  "jobId": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
  "credits_refunded": 300,
  "refund_pending": false
}

If the refund mechanism fails, refund_pending will be true and the refund will be retried automatically.

curl -X POST https://agent.media/api/v1/videos/a1b2c3d4-e5f6-7890-abcd-ef1234567890/cancel \
  -H "Authorization: Bearer ma_your_api_key"

GET/api/v1/actors

List available AI actors with optional filtering.

Query Parameters

ParameterTypeRequiredDefaultDescription
genderstringNo-Filter by gender (e.g. female, male)
age_rangestringNo-Filter by age range (e.g. 18-25, 26-35)
actor_typestringNo-Filter by type (e.g. Young Adult)
searchstringNo-Search by name (case-insensitive)

Response (200)

{
  "actors": [
    {
      "id": "66ac63f6-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
      "name": "Emma",
      "slug": "emma",
      "gender": "female",
      "age_range": "26-35",
      "actor_type": "Young Adult",
      "portrait_url": "https://pub-xxx.r2.dev/actors/emma/portrait.png",
      "voice_id": "EXAVITQu4vr4xnSDxMaL",
      "status": "active"
    }
  ],
  "total": 200
}
# List all female actors
curl "https://agent.media/api/v1/actors?gender=female" \
  -H "Authorization: Bearer ma_your_api_key"

GET/api/v1/actors/:slug

Get a single actor by slug. Returns similar slug suggestions on 404.

Response (200)

{
  "actor": {
    "id": "66ac63f6-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
    "name": "Emma",
    "slug": "emma",
    "gender": "female",
    "age_range": "26-35",
    "portrait_url": "https://pub-xxx.r2.dev/actors/emma/portrait.png",
    "voice_id": "EXAVITQu4vr4xnSDxMaL",
    "status": "active"
  }
}
curl https://agent.media/api/v1/actors/emma \
  -H "Authorization: Bearer ma_your_api_key"

GET/api/v1/account

Get account info including plan, credits, and feature limits.

Response (200)

{
  "user_id": "user-uuid",
  "plan": {
    "tier": "starter",
    "name": "Creator",
    "status": "active",
    "trial_active": false,
    "trial_ends_at": null,
    "current_period_end": "2026-04-20T00:00:00.000Z"
  },
  "credits": {
    "monthly_remaining": 2400,
    "monthly_allowance": 3900,
    "purchased": 0,
    "total": 2400
  },
  "limits": {
    "max_concurrent_jobs": 3,
    "max_video_duration": 10,
    "models_available": ["ugc-basic"]
  }
}

Plan Tiers

TierNameMonthly CreditsMax JobsMax Duration
freeFree015s
paygPay As You Go0215s
starterCreator3,900310s
creatorPro6,900515s
pro_plusPro Plus12,9001015s
curl https://agent.media/api/v1/account \
  -H "Authorization: Bearer ma_your_api_key"

GET/api/v1/account/usage

Get usage statistics for your account over a specified time period.

Query Parameters

ParameterTypeRequiredDefaultDescription
periodstringNo30dTime period: 7d, 30d, or 90d

Response (200)

{
  "period": "30d",
  "period_start": "2026-02-21T00:00:00.000Z",
  "period_end": "2026-03-23T00:00:00.000Z",
  "summary": {
    "total_jobs": 45,
    "completed_jobs": 40,
    "failed_jobs": 3,
    "credits_used": 12000
  },
  "by_model": [
    { "model_slug": "ugc-basic", "job_count": 45, "credits_used": 12000, "avg_duration_seconds": 85.2 }
  ],
  "daily": [
    { "date": "2026-03-22", "job_count": 3, "credits_used": 900 }
  ],
  "by_operation": [
    { "operation": "ugc_video", "job_count": 45 }
  ]
}
curl "https://agent.media/api/v1/account/usage?period=7d" \
  -H "Authorization: Bearer ma_your_api_key"

POST/api/v1/account/keys

Create a new API key. The full key is returned only once -- store it securely.

Request Body

ParameterTypeRequiredDefaultDescription
namestringNoDefaultKey name (max 100 characters)

Response (201)

{
  "key": "ma_a1b2c3d4e5f6789012345678901234ab",
  "id": "key-uuid",
  "key_prefix": "ma_a1b2c3d4",
  "name": "Production Key",
  "created_at": "2026-03-23T10:00:00.000Z"
}

Maximum 25 active keys per account. The full key value is shown only at creation.

curl -X POST https://agent.media/api/v1/account/keys \
  -H "Authorization: Bearer ma_your_api_key" \
  -H "Content-Type: application/json" \
  -d '{"name": "Production Key"}'

GET/api/v1/account/keys

List all active API keys. Returns metadata only -- the full key is never returned after creation.

Response (200)

{
  "keys": [
    {
      "id": "key-uuid",
      "key_prefix": "ma_a1b2c3d4",
      "name": "Production Key",
      "created_at": "2026-03-23T10:00:00.000Z",
      "last_used_at": "2026-03-23T14:30:00.000Z"
    }
  ]
}
curl https://agent.media/api/v1/account/keys \
  -H "Authorization: Bearer ma_your_api_key"

DELETE/api/v1/account/keys/:keyId

Revoke an API key. The key can no longer be used for authentication.

Path Parameters

ParameterTypeRequiredDefaultDescription
keyIdstringYes-Key ID (UUID) from creation or listing

Response (200)

{
  "revoked": true,
  "id": "key-uuid"
}
curl -X DELETE https://agent.media/api/v1/account/keys/key-uuid-here \
  -H "Authorization: Bearer ma_your_api_key"

Subtitle Styles

The style parameter on video creation accepts these 17 values:

StyleDescription
hormoziYellow karaoke-style highlight (default)
minimalClean white text, minimal animation
boldNeon cyan bold text
karaokeGreen pop karaoke highlighting
cleanWhite text on dark background
tiktokTikTok-native subtitle style
neonNeon glow effect
fireFire/flame animated text
glowSoft glow effect
popPop-in animation
aestheticAesthetic/pastel style
impactImpact font, bold white
pastelPastel color palette
electricElectric/lightning effect
boxedText in colored boxes
gradientGradient-colored text
spotlightSpotlight highlight effect

Credit Costs

Videos are billed at 30 credits/second, rounded up to the nearest duration bucket.

DurationCreditsUSD Equivalent
5s150~$1.50
10s300~$3.00
15s450~$4.50

AI script generation (using prompt) adds +5 credits. Credits are deducted immediately and refunded on failure or cancellation.


Errors

HTTP StatusError TypeDescription
400validation_errorInvalid or missing request parameters
401authentication_errorMissing or invalid API key
402insufficient_creditsNot enough credits for the operation
403authentication_errorForbidden (plan tier too low)
404not_foundResource not found
429rate_limit_errorToo many requests -- check Retry-After header
500server_errorInternal server error
502server_errorEdge function unreachable

Common Error Codes

CodeWhen
missing_api_keyNo Authorization header provided
invalid_jsonRequest body is not valid JSON
missing_scriptNeither script nor prompt was provided
cta_too_longCTA text exceeds 100 characters
job_not_foundVideo job ID does not exist or belongs to another user
cannot_cancelJob is already in a terminal state
plan_requiredUser plan tier too low for UGC videos
plan_limitRequested duration exceeds plan limit
insufficient_creditsNot enough credits for the video
edge_function_unreachableBackend service temporarily unavailable

Important Notes

  • Max video duration is 15 seconds. Valid values for target_duration are 5, 10, or 15.
  • Videos are generated asynchronously. Use polling (GET /videos/:id every 5s) or provide a webhook_url.
  • Credits are deducted immediately on job creation and refunded automatically on failure or cancellation.
  • Voice is auto-selected based on the chosen actor. The voice, tts_provider, persona_slug, and face_photo_url parameters are not exposed via the REST API.
  • Starter/Creator plans are limited to 10s. Pro and Pro Plus support the full 15s duration.
  • API keys use the ma_ prefix and are hashed with SHA-256. The full key is only shown once at creation.
© 2026 agent-media. All rights reserved.