ApiframeApiframe Docs

Assets

Pre-upload media files for use as references in video generation.

The Assets API lets you pre-upload images, videos, and audio files into provider storage. Once uploaded, reference them in generation requests using asset://{assetId} URIs instead of direct URLs.

This is useful for Seedance 2.0 multimodal references (reference_image_urls, reference_video_urls, reference_audio_urls, start_image, end_image) where the source media may be large or behind authentication.

Create an asset

POST /v2/assets/create

Upload a media file by providing its URL. The file is fetched and stored by the provider asynchronously.

Request body

FieldTypeRequiredDescription
urlstringYesPublic URL of the media file to upload
typestringYesMedia type: "image", "video", or "audio"

Response

Status: 201 Created

{
  "assetId": "abc123def456"
}

Get asset status

GET /v2/assets/:assetId

Check the processing status of an uploaded asset.

Response

Status: 200 OK

{
  "status": "Active",
  "url": "https://storage.provider.com/...",
  "errorMsg": null
}
StatusMeaning
ProcessingThe asset is still being uploaded and processed
ActiveReady to use — reference as asset://{assetId}
FailedUpload failed — check errorMsg for details

Usage in generation requests

Once an asset reaches Active status, use it in any field that accepts media URLs:

{
  "prompt": "A person dancing to upbeat music",
  "model": "seedance-2",
  "seedanceParams": {
    "reference_audio_urls": ["asset://abc123def456"],
    "reference_image_urls": ["asset://xyz789", "https://example.com/photo.jpg"]
  }
}

You can mix asset:// URIs with direct URLs in the same request.

Code examples

# 1. Create an asset
curl -X POST https://api.apiframe.ai/v2/assets/create \
  -H "X-API-Key: afk_your_api_key_here" \
  -H "Content-Type: application/json" \
  -d '{"url": "https://example.com/reference.mp4", "type": "video"}'

# 2. Check status
curl https://api.apiframe.ai/v2/assets/abc123def456 \
  -H "X-API-Key: afk_your_api_key_here"
import requests
import time

headers = {
    "X-API-Key": "afk_your_api_key_here",
    "Content-Type": "application/json",
}

# 1. Create an asset
resp = requests.post(
    "https://api.apiframe.ai/v2/assets/create",
    headers=headers,
    json={"url": "https://example.com/reference.mp4", "type": "video"},
)
asset_id = resp.json()["assetId"]

# 2. Poll until active
while True:
    status = requests.get(
        f"https://api.apiframe.ai/v2/assets/{asset_id}",
        headers=headers,
    ).json()
    if status["status"] == "Active":
        break
    time.sleep(2)

# 3. Use in generation
requests.post(
    "https://api.apiframe.ai/v2/videos/generate",
    headers=headers,
    json={
        "prompt": "A cinematic scene inspired by the reference",
        "model": "seedance-2",
        "seedanceParams": {
            "reference_video_urls": [f"asset://{asset_id}"],
        },
    },
)
const headers = {
  "X-API-Key": "afk_your_api_key_here",
  "Content-Type": "application/json",
};

// 1. Create an asset
const createResp = await fetch("https://api.apiframe.ai/v2/assets/create", {
  method: "POST",
  headers,
  body: JSON.stringify({ url: "https://example.com/reference.mp4", type: "video" }),
});
const { assetId } = await createResp.json();

// 2. Poll until active
let status;
do {
  await new Promise((r) => setTimeout(r, 2000));
  const resp = await fetch(`https://api.apiframe.ai/v2/assets/${assetId}`, { headers });
  status = await resp.json();
} while (status.status !== "Active");

// 3. Use in generation
await fetch("https://api.apiframe.ai/v2/videos/generate", {
  method: "POST",
  headers,
  body: JSON.stringify({
    prompt: "A cinematic scene inspired by the reference",
    model: "seedance-2",
    seedanceParams: {
      reference_video_urls: [`asset://${assetId}`],
    },
  }),
});

On this page