TikTok
Supports public single videos and photo posts.
tiktok.com/@user/video/{id}tiktok.com/@user/photo/{id}tiktok.com/t/{shortCode}vm.tiktok.com/{code} or other TikTok share linksProfiles, live pages, and TikTok Lite pages are not supported.
Easydown API
Easydown API は、バックエンド、スクリプト、自動化サービスから公開メディアリンクを統一形式で解析するための API です。
POST https://api.easydown.org/api/v1/parse
Private API token を Bearer token として送信します。ed_live token をブラウザ JavaScript に埋め込まないでください。
Authorization
Bearer ed_live_xxx
Content-Type
application/json
curl -X POST https://api.easydown.org/api/v1/parse \
-H "Authorization: Bearer ed_live_xxx" \
-H "Content-Type: application/json" \
-d '{"url":"https://www.instagram.com/reel/..."}'{
"url": "https://www.instagram.com/reel/..."
}All platforms use the same parse endpoint. The formats below are recognized as public single-media links; final results still depend on whether the content is public and available.
Supports public single videos and photo posts.
tiktok.com/@user/video/{id}tiktok.com/@user/photo/{id}tiktok.com/t/{shortCode}vm.tiktok.com/{code} or other TikTok share linksProfiles, live pages, and TikTok Lite pages are not supported.
Supports public videos, image notes, share links, and selected Douyin CDN media URLs.
v.douyin.com/{code}douyin.com/video/{id}douyin.com/share/video/{id}douyin.com/note/{id}douyin.com/share/note/{id}douyin.com/shipin/{id}douyin.com/vsdetail/{id}douyinpic.com / douyinvod.com / douyinstatic.com media URLsProfiles, search, collections, follow pages, and live pages are not supported.
Supports public single video, Shorts, and live replay URLs that resolve to a video id.
youtu.be/{id}youtube.com/watch?v={id}youtube.com/shorts/{id}youtube.com/live/{id}Playlists, channels, community posts, and private videos are not supported.
Supports public post URLs with a status id.
x.com/{user}/status/{id}twitter.com/{user}/status/{id}Profiles, search pages, spaces, and direct media CDN URLs are not treated as posts.
Supports public posts, Reels, videos, photos, carousels, embeds, and share redirects.
instagram.com/p/{code}instagram.com/reel/{code}instagram.com/reels/{code}instagram.com/tv/{code}instagram.com/{username}/p/{code}instagram.com/{username}/reel/{code}instagram.com/p/{code}/embedinstagram.com/r/{code}instagram.com/share/...Stories, Highlights, profiles, direct messages, Explore pages, and private content are not supported.
Supports public notes, including video and image note links.
xhslink.com/{code}xiaohongshu.com/explore/{noteId}xiaohongshu.com/discovery/item/{noteId}Share text containing a Xiaohongshu URLProfiles, search pages, collections, and private notes are not supported.
Supports public video pages, short links, list pages with bvid, and selected playable pages.
bilibili.com/video/BV...bilibili.com/video/av...b23.tv/{code}bili.im/{code}bilibili.com/list/...?...bvid=BV...bilibili.com/bangumi/play/ep...bilibili.com/bangumi/play/ss...bilibili.com/cheese/play/ss...Watchlater lists, favorites, profile pages, and list pages without a single video id are not supported.
Supports public single Kuaishou video links and share text.
kuaishou.com/short-video/{photoId}kuaishou.com/f/{token}v.kuaishou.com/{token}gifshow.com/fw/photo/{photoId}chenzhongtech.com/fw/photo/{photoId}Share text containing a Kuaishou URLProfiles, search pages, collections, live pages, and private videos are not supported.
Supports public Weibo posts with videos, images, or image galleries.
weibo.com/{uid}/{postId}weibo.com/{uid}/{mblogid}m.weibo.cn/status/{id}weibo.com/tv/show/1034:{id}video.weibo.com/show?fid=1034:{id}t.cn/{code}mapp.api.weibo.cn/fx/...Share text containing a Weibo URLProfiles, search pages, topics, super topics, live pages, articles, and collections are not supported.
API key can be permanent or expire on a selected date. Leaving expiration blank means it never expires. You can limit a key to selected platforms; All platforms allows every supported platform. Edit changes name, expiration, and platform permissions without changing the token value. Reset rotates the token value while keeping permissions.
{
"status": 200,
"data": {
"platform": "instagram",
"title": "Example title",
"thumbnail": "https://...",
"duration": 12,
"images": [
{
"url": "https://...",
"width": 1080,
"height": 1350
}
],
"videos": [
{
"url": "https://...",
"quality": "HD",
"mimeType": "video/mp4",
"width": 1080,
"height": 1920,
"hasAudio": true,
"source": "direct"
}
],
"audios": []
},
"msg": "success"
}{
"status": 401,
"data": null,
"msg": "Unauthorized",
"code": "missing_token"
}| Field | Type | Description |
|---|---|---|
| platform | string | Normalized platform name such as instagram or youtube. |
| title | string | Media title or caption when available. |
| thumbnail | string | Preview image URL when available. |
| duration | number | Duration in seconds. Images and galleries usually return 0. |
| images[] | array | Downloadable image items with url, width, and height. |
| videos[] | array | Downloadable video items with url, quality, mimeType, dimensions, hasAudio, and source. |
| audios[] | array | Downloadable audio items when the platform exposes audio separately. |
Easydown API returns media URLs in images[], videos[], and audios[]. These URLs come from the original platform and may be affected by expiration, anti-hotlinking, CORS, cookies, region limits, or split audio/video streams.
Many media CDNs validate Origin, Referer, cookies, IP region, and request headers. A URL may work from your server but fail in browser JavaScript with CORS, CORP, 403, 404, or an empty file.
| Platform | Recommended headers | Cookie needed? | Special handling | Expiration notes |
|---|---|---|---|---|
| Douyin | Referer: https://www.douyin.com/; browser User-Agent; forward Range when present. | Usually no | Use server-side streaming for video and image-note media. | URLs are short lived. Re-parse when a link returns 403 or 404. |
| TikTok | Referer: https://www.tiktok.com/; browser User-Agent. | Sometimes | Some web media requires a valid access cookie such as tt_chain_token from your own browsing context. Region-restricted links may require an accessible server region. | Re-parse and retry when direct access fails. |
| Bilibili | Referer: https://www.bilibili.com/; browser User-Agent; forward Range. | For some high-quality or account-limited streams | DASH results can return separate video and audio URLs. Download both and merge with FFmpeg. | Re-parse when signed stream URLs expire. |
| Xiaohongshu | Referer: https://www.xiaohongshu.com/; browser User-Agent. | Sometimes | Image and video CDNs can enforce strict anti-hotlinking. Download through your backend. | Re-parse when the CDN URL becomes invalid. |
| Referer: https://weibo.com/ or https://m.weibo.cn/; browser User-Agent. | Usually no | Choose the quality URL that matches your product needs when multiple URLs are returned. | Image and video URLs can expire. Re-parse to refresh. | |
| YouTube | Referer: https://www.youtube.com/; Origin: https://www.youtube.com; browser User-Agent. | For protected or age/account-limited content | High-quality streams are often split into audio and video. Merge separated streams with FFmpeg. | Some streams are bound to region or IP. Use an accessible server region and re-parse when needed. |
| Referer: https://www.instagram.com/; browser User-Agent. | Sometimes | Browser preview can hit CORS or CORP. Use backend proxy downloads for stable delivery. | CDN URLs may expire. Re-parse public posts when needed. | |
| Kuaishou | Referer: https://www.kuaishou.com/; browser User-Agent; forward Range. | Usually no | Use server-side streaming for large short-video files. | Media URLs can expire. Re-parse the public video link. |
| X / Twitter | Referer: https://x.com/; browser User-Agent. | Usually no | Video media may include multiple bitrates. Select the quality that fits your use case. | Re-parse when selected media variants fail. |
Node.js / Next.js proxy route
// app/api/media-proxy/route.js
const PLATFORM_HEADERS = {
douyin: {
Referer: 'https://www.douyin.com/',
'User-Agent': 'Mozilla/5.0 AppleWebKit/537.36 Chrome/120 Safari/537.36',
},
tiktok: {
Referer: 'https://www.tiktok.com/',
'User-Agent': 'Mozilla/5.0 AppleWebKit/537.36 Chrome/120 Safari/537.36',
},
bilibili: {
Referer: 'https://www.bilibili.com/',
'User-Agent': 'Mozilla/5.0 AppleWebKit/537.36 Chrome/120 Safari/537.36',
},
xiaohongshu: {
Referer: 'https://www.xiaohongshu.com/',
'User-Agent': 'Mozilla/5.0 AppleWebKit/537.36 Chrome/120 Safari/537.36',
},
weibo: {
Referer: 'https://weibo.com/',
'User-Agent': 'Mozilla/5.0 AppleWebKit/537.36 Chrome/120 Safari/537.36',
},
youtube: {
Referer: 'https://www.youtube.com/',
Origin: 'https://www.youtube.com',
'User-Agent': 'Mozilla/5.0 AppleWebKit/537.36 Chrome/120 Safari/537.36',
},
instagram: {
Referer: 'https://www.instagram.com/',
'User-Agent': 'Mozilla/5.0 AppleWebKit/537.36 Chrome/120 Safari/537.36',
},
kuaishou: {
Referer: 'https://www.kuaishou.com/',
'User-Agent': 'Mozilla/5.0 AppleWebKit/537.36 Chrome/120 Safari/537.36',
},
twitter: {
Referer: 'https://x.com/',
'User-Agent': 'Mozilla/5.0 AppleWebKit/537.36 Chrome/120 Safari/537.36',
},
};
export async function GET(request) {
const { searchParams } = new URL(request.url);
const mediaUrl = searchParams.get('url');
const platform = searchParams.get('platform');
if (!mediaUrl || !platform || !PLATFORM_HEADERS[platform]) {
return Response.json({ error: 'invalid_request' }, { status: 400 });
}
const range = request.headers.get('range');
const headers = { ...PLATFORM_HEADERS[platform] };
if (range) headers.Range = range;
const mediaResponse = await fetch(mediaUrl, { headers });
if (!mediaResponse.ok || !mediaResponse.body) {
return Response.json(
{ error: 'download_failed', status: mediaResponse.status },
{ status: 502 }
);
}
const responseHeaders = new Headers();
const contentType = mediaResponse.headers.get('content-type');
const contentLength = mediaResponse.headers.get('content-length');
const contentRange = mediaResponse.headers.get('content-range');
if (contentType) responseHeaders.set('Content-Type', contentType);
if (contentLength) responseHeaders.set('Content-Length', contentLength);
if (contentRange) responseHeaders.set('Content-Range', contentRange);
responseHeaders.set('Accept-Ranges', 'bytes');
responseHeaders.set('Cache-Control', 'private, max-age=300');
return new Response(mediaResponse.body, {
status: mediaResponse.status,
headers: responseHeaders,
});
}Browser usage
// Browser code: call your own backend, not the platform CDN directly.
const downloadUrl = new URL('/api/media-proxy', window.location.origin);
downloadUrl.searchParams.set('platform', media.platform);
downloadUrl.searchParams.set('url', media.videos[0].url);
window.location.href = downloadUrl.toString();Merging separated audio and video
# When video and audio are returned separately, download both files first.
ffmpeg -i video.mp4 -i audio.m4a -c copy output.mp4成功した解析は 1 credit を消費します。失敗、非対応リンク、認証エラー、プラットフォーム側の応答失敗では credits は消費されません。
API は公開された単一投稿メディア向けです。非公開投稿、削除済みコンテンツ、地域制限、ライブ配信、プロフィール、検索ページ、コレクションページは対象外です。
| HTTP | Code | Meaning |
|---|---|---|
| 401 | missing_token / invalid_token | Authorization header is missing or the token is invalid. |
| 401 | token_expired | The API token has passed its expiration date. Edit the key or create a new one. |
| 403 | platform_not_allowed | The API token is not allowed to access the platform detected from the URL. |
| 402 | insufficient_credits | The account does not have enough credits for a successful parse. |
| 400 | 302 | The URL format is unsupported or not a single supported media post. |
| 200 | 304 | Easydown could not return downloadable media for this public link. |
Need integration help? Join Telegram or Discord support.