# Douyin Video Downloader API – Direct Video & Audio URLs (`lance_api/douyin-video-downloader-api`) Actor

Resolve public Douyin videos into direct video and audio URLs. Supports video links, short URLs, share text, and aweme IDs, with batch processing, optional metadata, and pay-per-successful-result pricing.

- **URL**: https://apify.com/lance\_api/douyin-video-downloader-api.md
- **Developed by:** [LanceAPI](https://apify.com/lance_api) (community)
- **Categories:**
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

$2.90 / 1,000 results

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.
Actors are written with capital "A".

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

## Douyin Video Downloader API

Turn public Douyin video links into direct video and audio URLs you can immediately use in downloaders, apps, bots, SaaS products, and automated workflows.

Submit a Douyin video URL, short link, share text, or aweme ID. The Actor resolves the work, validates the direct video URL, and returns a clean media-first result.

Returns direct media URLs — it does not copy the video file into Apify storage.

Pay only for successful results — failed, unavailable, and duplicate works are not charged.

This is an unofficial Actor and is not affiliated with, endorsed by, or sponsored by Douyin or ByteDance.

### Key features

- **Direct downloadable video URL:** Resolve a public Douyin work into a validated `videoUrl` ready for downstream download or playback.
- **Audio URL when available:** Get a separate direct audio URL when Douyin exposes one; otherwise `audioUrl` remains `null`.
- **Multiple input formats:** Use full video/note URLs, `v.douyin.com` short links, `iesdouyin.com` share links, copied share text, modal URLs, or bare aweme IDs.
- **Media-first output:** Receive `videoUrl`, `audioUrl`, `coverUrl`, and `duration` at the top level. Enable `includeMetadata` only when you need extended data.
- **Independent batch processing:** Process up to 1,000 inputs in one run. One invalid or unavailable URL does not stop the rest of the batch.
- **No media copy or transcoding:** URLs are resolved, not transcoded with FFmpeg or copied into Apify storage.

### Quick start

1. Add public Douyin links to `urls`.
2. For the smallest and fastest response, leave `includeMetadata` disabled.
3. Click **Start**.
4. Open **Output** and use `videoUrl`, `audioUrl`, or `coverUrl`.

```json
{
  "urls": [
    "https://www.douyin.com/video/7534679152504376595"
  ],
  "includeMetadata": false
}
```

### Supported inputs

| Input type | Example |
| --- | --- |
| Video URL | `https://www.douyin.com/video/7534679152504376595` |
| Note URL | `https://www.douyin.com/note/7534679152504376595` |
| Share URL | `https://www.iesdouyin.com/share/video/7534679152504376595` |
| Short link | `https://v.douyin.com/.../` |
| Modal URL | `https://www.douyin.com/jingxuan?modal_id=7534679152504376595` |
| Share text | Copied Douyin text containing a supported URL |
| Aweme ID | `7534679152504376595` |

`discover?modal_id=...`, supported note/slides share variants, and Markdown-wrapped links such as `[URL](URL)` are also accepted.

A Note URL is supported when the resolved work contains downloadable video media. An image-only note cannot produce a successful Downloader result.

### Input

| Field | Type | Required | Default | Limits | Description |
| --- | --- | --- | --- | --- | --- |
| `urls` | `array[string]` | Yes | — | 1–1,000 | Public Douyin work URLs, short/share links, copied share text, or bare aweme IDs. |
| `includeMetadata` | `boolean` | No | `false` | — | Add description, timestamps, creator, engagement, music, and hashtags inside `metadata`. |

### Default output

Each unique work produces one Dataset item. Core media fields remain top-level in both output modes. The example below is based on a real public Douyin work; temporary signed query parameters are shortened because media URLs may expire.

```json
{
  "input": "https://www.douyin.com/video/7534679152504376595",
  "normalizedUrl": "https://www.douyin.com/video/7534679152504376595",
  "awemeId": "7534679152504376595",
  "title": "雨天开车秒变“睁眼瞎”？玻璃起雾别慌！3步极速除雾法， 新手必存...",
  "contentType": "video",
  "videoUrl": "https://www.douyin.com/aweme/v1/play/?...temporary-parameters...",
  "audioUrl": "https://sf6-cdn-tos.douyinstatic.com/obj/ies-music/7534679156710247206.mp3",
  "coverUrl": "https://p3-pc-sign.douyinpic.com/...jpeg?...temporary-parameters...",
  "duration": 67.756,
  "success": true,
  "status": "success",
  "error": null,
  "resolvedAt": "2026-09-01T...Z"
}
```

The direct `videoUrl` must pass a lightweight HEAD or Range request before a Downloader result is successful. If a separate audio URL is unavailable or fails validation, `audioUrl` is `null`; the Actor never invents an MP3 URL.

### Output with metadata

Set `includeMetadata` to `true`. Media fields stay top-level; extended data is added under `metadata`. Enabling metadata does not increase result pricing.

```json
{
  "input": "https://www.douyin.com/video/7534679152504376595",
  "normalizedUrl": "https://www.douyin.com/video/7534679152504376595",
  "awemeId": "7534679152504376595",
  "title": "雨天开车秒变“睁眼瞎”？玻璃起雾别慌！3步极速除雾法， 新手必存...",
  "contentType": "video",
  "videoUrl": "https://www.douyin.com/aweme/v1/play/?...temporary-parameters...",
  "audioUrl": "https://sf6-cdn-tos.douyinstatic.com/obj/ies-music/7534679156710247206.mp3",
  "coverUrl": "https://p3-pc-sign.douyinpic.com/...jpeg?...temporary-parameters...",
  "duration": 67.756,
  "metadata": {
    "description": "雨天开车秒变“睁眼瞎”？玻璃起雾别慌！3步极速除雾法， 新手必存...",
    "createTime": 1754304200,
    "createTimeIso": "2025-08-04T10:43:20.000Z",
    "author": { "nickname": "懂车小彬", "followerCount": 384795, "totalFavorited": 3717158 },
    "engagement": { "playCount": 0, "diggCount": 11993, "commentCount": 617, "shareCount": 4887, "collectCount": 13171, "recommendCount": 472 },
    "music": { "title": "@懂车小彬创作的原声", "author": "懂车小彬", "duration": 67 },
    "hashtags": ["雨天开车除雾正确方法", "新手司机", "新手开车", "青年创作者成长计划"]
  },
  "success": true,
  "status": "success",
  "error": null,
  "resolvedAt": "2026-09-01T...Z"
}
```

The sample's `playCount: 0` is not a fallback value: Douyin explicitly returned the `playCount` field with a value of `0` for that work. When a supported metric is absent from the source response, the Actor returns `null` instead of inventing a zero.

### Output field reference

| Field | Type | Description |
| --- | --- | --- |
| `input` | string | Original input supplied for this result. |
| `normalizedUrl` | string or null | Canonical Douyin video or note URL after resolution. |
| `awemeId` | string or null | Unique Douyin work ID. |
| `title` | string or null | Work description used as its display title. |
| `contentType` | string or null | Normalized type: `video`, `image`, or `unknown`. |
| `videoUrl` | string or null | Preferred direct video URL. A successful Downloader item requires this URL to pass lightweight validation. |
| `audioUrl` | string or null | Separate direct audio URL when genuinely exposed and accessible. |
| `coverUrl` | string or null | Cover or preview image URL. |
| `duration` | number or null | Video duration in seconds. |
| `metadata` | object | Extended data included only when `includeMetadata` is `true`. |
| `success` | boolean | Whether a validated direct video result was produced. |
| `status` | string | Stable result classification for automation and error handling. |
| `error` | object or null | Safe error code and message; `null` on success. |
| `resolvedAt` | string | ISO 8601 timestamp when processing completed. |

#### Metadata fields

| Field | Description |
| --- | --- |
| `description` | Full work description when available. |
| `createTime` | Source creation time as a Unix timestamp. |
| `createTimeIso` | Source creation time in ISO 8601 format. |
| `author` | Available creator nickname, avatar, follower count, and total favorites. |
| `engagement` | Available play, like, comment, share, collect, and recommendation counts. Missing values are `null`. |
| `music` | Available music title, author, direct audio URL, and duration. |
| `hashtags` | Hashtag names extracted from the work detail. |
| `images` | Image URLs when an image/note work exposes them reliably. |

### Status and errors

| Status | Meaning | Charged? |
| --- | --- | --- |
| `success` | A direct video URL was resolved and passed lightweight validation. | Yes |
| `media_unavailable` | Metadata may exist, but no validated video URL is available. | No |
| `duplicate` | The same aweme ID was already processed in this run. | No |
| `invalid_input` / `unsupported_url` | Input is malformed or unsupported. | No |
| `not_found` / `unavailable` / `private` | The work cannot be accessed publicly. | No |
| `blocked` / `login_required` / `rate_limited` | Douyin rejected or limited the anonymous request. | No |
| `timeout` / `upstream_error` / `parsing_failed` | A temporary request or response parsing problem occurred. | No |
| `internal_error` | An unexpected safe-to-report processing error occurred. | No |

If a long link, short link, share URL, or share text resolves to an aweme ID already processed in the same run, only the first unique work can be billed. A returned `duplicate` Dataset item is not charged.

```json
{
  "input": "not a Douyin URL",
  "normalizedUrl": null,
  "awemeId": null,
  "success": false,
  "status": "invalid_input",
  "error": {
    "code": "INVALID_INPUT",
    "message": "The input does not contain a supported Douyin URL."
  },
  "resolvedAt": "2026-09-01T...Z"
}
```

### API examples

JavaScript:

```javascript
import { ApifyClient } from 'apify-client';

const client = new ApifyClient({ token: process.env.APIFY_TOKEN });
const run = await client.actor('lance_api/douyin-video-downloader-api').call({
  urls: ['https://www.douyin.com/video/7534679152504376595'],
  includeMetadata: false,
});
const { items } = await client.dataset(run.defaultDatasetId).listItems();
console.log(items);
```

Python:

```python
import os
from apify_client import ApifyClient

client = ApifyClient(os.environ['APIFY_TOKEN'])
run = client.actor('lance_api/douyin-video-downloader-api').call(run_input={
    'urls': ['https://www.douyin.com/video/7534679152504376595'],
    'includeMetadata': False,
})
items = client.dataset(run['defaultDatasetId']).list_items().items
print(items)
```

cURL:

```bash
curl -X POST \
  'https://api.apify.com/v2/acts/lance_api~douyin-video-downloader-api/run-sync-get-dataset-items' \
  -H 'Authorization: Bearer APIFY_TOKEN' \
  -H 'Content-Type: application/json' \
  -d '{"urls":["https://www.douyin.com/video/7534679152504376595"],"includeMetadata":false}'
```

### Pricing

This Actor uses **result-based pricing**.

**Just $0.0029 per successful video — $2.90 per 1,000 successful results.**

A `result` event is charged only when the Actor successfully resolves a valid direct video URL and writes the successful result to the Dataset.

You are **not charged** for:

- Invalid or unsupported inputs
- Unavailable or private works
- Blocked, rate-limited, timed-out, or failed requests
- Media that cannot produce a validated `videoUrl`
- Duplicate works within the same run

`includeMetadata: true` does **not** create an additional charge.

**One successful Douyin work = one result charge.**

### Use cases

- **Video download tools:** Use `videoUrl` as the downloadable source in your own downloader workflow.
- **Content archiving:** Resolve public media URLs for archiving workflows where you have permission to store the content.
- **SaaS products:** Add Douyin video resolution to media products without maintaining your own resolver.
- **Bots and automation:** Feed direct media URLs into Telegram or Discord bots, workflow tools, and internal automations.
- **Media processing pipelines:** Pass resolved URLs into your own FFmpeg, transcription, moderation, or storage pipeline.
- **AI video workflows:** Feed resolved Douyin media into speech-to-text, video understanding, summarization, or multimodal AI pipelines.
- **Dataset enrichment:** Collect optional creator, engagement, music, and hashtag metadata together with media URLs.

### Use with AI agents

Use this Actor through the Apify MCP Server from compatible AI clients and agent workflows to resolve Douyin links into structured media URLs.

An AI agent can accept a Douyin link, resolve the media URL with this Actor, and pass it to downstream transcription, video analysis, moderation, or storage tools.

### FAQ

#### Does this Actor download the video file into Apify storage?

No. It returns direct media URLs. Your application can download permitted media from those URLs if persistent storage is required.

#### Does it support Douyin short links and copied share text?

Yes. It supports `v.douyin.com` short links, `iesdouyin.com` share links, copied share text, and the other formats listed above.

#### Does it require a Douyin Cookie?

No user Cookie is required. The Actor uses an anonymous request flow.

#### Does it support private videos?

No. It processes publicly accessible individual works only.

#### Are the returned media URLs permanent?

No. Direct media and signed cover URLs may expire, so use or store permitted media promptly.

#### Does `includeMetadata` cost extra?

No. It does not create an additional result charge.

#### What happens when no separate audio URL is available?

`audioUrl` is `null`. The Actor does not construct or guess an MP3 URL.

#### Does the returned video include audio?

The selected `videoUrl` normally points to a playable video that already includes audio when the source provides it. The separate `audioUrl` is optional and is useful when a workflow needs the audio track on its own. Douyin media variants can change, so integrations that require a guaranteed stream layout should inspect the returned media file.

#### Are failed inputs or duplicates charged?

No. Only a unique successful work with a validated `videoUrl` is charged.

#### How much does it cost?

$0.0029 per successful result — $2.90 per 1,000 successful results.

### Limitations

- Media URLs may expire. Download permitted media promptly if you need durable storage.
- The Actor resolves direct media URLs; it does not copy the media file into Apify storage.
- Public individual works only; no profiles, search, feeds, comments, private works, or login Cookie input.
- Image/note metadata may be returned by the shared resolver, but Downloader success requires a validated `videoUrl`.
- Douyin can change page data, rate-limit requests, or apply regional and age restrictions.
- Dataset order is not guaranteed for concurrent batches. Match items using `input` or `awemeId`.

### Responsible use

Use only for content you are legally permitted to access and download. Respect copyright, privacy, applicable law, and platform terms.

### Support

Contact <lanceapi2026@hotmail.com> or open an issue on the Actor page.

Include the run ID, a safe input URL, the returned `status`, and `error.code`. Never send Apify tokens, cookies, signatures, authorization headers, passwords, or proxy credentials. Keep API tokens out of source code, screenshots, prompts, and logs.

# Actor input Schema

## `urls` (type: `array`):

Add 1–1000 public Douyin video or note links. Full douyin.com URLs, iesdouyin.com share links, v.douyin.com short links, jingxuan/discover links, copied share text, Markdown-wrapped links, and bare aweme IDs are supported. Each item is processed independently, so one invalid URL does not stop the batch.

## `includeMetadata` (type: `boolean`):

Return extended Douyin video metadata in addition to the default direct media URLs. Disabled by default to keep downloader output minimal.

## Actor input object example

```json
{
  "urls": [
    "https://www.douyin.com/video/7534679152504376595"
  ],
  "includeMetadata": false
}
```

# Actor output Schema

## `results` (type: `string`):

Direct video, audio, and cover URLs for each processed unique Douyin work.

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "urls": [
        "https://www.douyin.com/video/7534679152504376595"
    ],
    "includeMetadata": false
};

// Run the Actor and wait for it to finish
const run = await client.actor("lance_api/douyin-video-downloader-api").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "urls": ["https://www.douyin.com/video/7534679152504376595"],
    "includeMetadata": False,
}

# Run the Actor and wait for it to finish
run = client.actor("lance_api/douyin-video-downloader-api").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "urls": [
    "https://www.douyin.com/video/7534679152504376595"
  ],
  "includeMetadata": false
}' |
apify call lance_api/douyin-video-downloader-api --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,lance_api/douyin-video-downloader-api"
        }
    }
}

```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/cfD4ldeAcX7OUgtFx/builds/K8HmiqoVTUbG08wIO/openapi.json
