GET /api/v2/anime/media-sources/

Media Sources

Playable video URLs (several resolutions) and subtitle tracks for one episode or movie.

Overview

Resolves an episode to direct video files and captions. URLs are signed and expire, so request them right before playback and don't cache them. Skip entries with vipLocked: true or an empty url. For a movie, pass se=0&ep=0. CDN URLs usually refuse hotlinking from browsers, so play them through the Stream Proxy.

GET https://api.animedoc.cloud/api/v2/anime/media-sources/
X-API-Key: <your key>

Parameters

NameInTypeRequiredDefaultDescription
subjectIdquerystringyes—subjectId from Search or Details.
detailPathquerystringyes—detailPath from Search or Details.
sequeryintegerno1Season number (0 for movies).
epqueryintegerno1Episode number (0 for movies).

Example request

cURL
curl "https://api.animedoc.cloud/api/v2/anime/media-sources/?subjectId=3325889774849773352&detailPath=naruto-2D7JgAQBGX3&se=1&ep=1" \
  -H "X-API-Key: $ANIMEDOC_API_KEY"
JavaScript (Node 18+)
const params = new URLSearchParams({"subjectId":"3325889774849773352","detailPath":"naruto-2D7JgAQBGX3","se":"1","ep":"1"});
const res = await fetch("https://api.animedoc.cloud/api/v2/anime/media-sources/?" + params, {
  headers: { "X-API-Key": process.env.ANIMEDOC_API_KEY },
});
const { data } = await res.json();
console.log(data);
Python
import os
import requests

res = requests.get(
    "https://api.animedoc.cloud/api/v2/anime/media-sources/",
    params={"subjectId":"3325889774849773352","detailPath":"naruto-2D7JgAQBGX3","se":1,"ep":1},
    headers={"X-API-Key": os.environ["ANIMEDOC_API_KEY"]},
    timeout=15,
)
res.raise_for_status()
print(res.json()["data"])

Example response

{
  "code": 0,
  "message": "ok",
  "data": {
    "downloads": [
      { "id": "1", "url": "https://cdn.../720.mp4?sign=...", "resolution": 720, "size": 145200000, "duration": 1380, "codecName": "h264", "vipLocked": false },
      { "id": "2", "url": "https://cdn.../480.mp4?sign=...", "resolution": 480, "size": 81000000, "duration": 1380, "codecName": "h264", "vipLocked": false }
    ],
    "captions": [
      { "id": "c1", "lan": "en", "lanName": "English", "url": "https://cdn.../en.srt" }
    ]
  }
}

Error codes

StatusBodyWhat it means
400{"error": "Missing detailPath query parameter"}A required parameter is missing or invalid.
401{"detail": "An API key is required. Send it as the X-API-Key header. ..."}No X-API-Key header, or the key doesn't exist (Invalid API key). Every catalog endpoint needs a key; get a free one at /docs/pricing.
403{"detail": "Playback through the API needs a paid plan ..."}Your plan doesn't include this endpoint. The stream proxy needs a paid plan.
404{"error": "No playable source is available ..."}The title or episode doesn't exist, or has no playable source right now.
429{"error": "rate_limit_exceeded"} or {"error": "daily_quota_exceeded"}Over your plan's requests per minute or per day. Wait Retry-After seconds, or upgrade.
502{"error": "...", "details": "..."}The content provider didn't answer in time. Safe to retry with backoff.

When you go over a limit you get 429 Too Many Requests with a Retry-After header (seconds):

HTTP/1.1 429 Too Many Requests
Retry-After: 34
Content-Type: application/json

{
  "error": "rate_limit_exceeded",
  "detail": "Your free plan allows 10 requests per minute. Slow down and retry in 34s.",
  "limit": 10,
  "window": "minute",
  "retry_after_seconds": 34,
  "upgrade_url": "https://animedoc.cloud/pricing"
}

Rate limits per plan

PlanRequests / dayRequests / minuteStream proxyPrice
Free2010No$0
Starter3,00060Yes$12/month or $60/6 months
Pro20,000300Yes$22/month or $110/6 months
Business500,000+CustomYesFrom $100/month
3-Day Pass2,00060Yes$1 for 3 days

Every call made with your API key counts as one request. Daily quotas reset at 00:00 UTC. See rate limits for headers and retry advice, or pricing to raise your limits.