Douyin Downloader: Batch-download Douyin content with SQLite and browser fallback
A Python tool for developers to batch-download Douyin content, using SQLite deduplication and browser fallback when post pagination is restricted.
GitHub jiji262/douyin-downloader Updated 2026-09-14 Branch main Stars 11.4K Forks 1.8K
Python Douyin downloading SQLite Playwright Docker macOS/Linux/Windows

🧭 Decision Guide

Try it if you

  • You need to batch-download post, like, mix, or music from a profile on Python 3.8+.
    The README's “Requirements” and “Feature Overview” list Python 3.8+ and four modes for `/user/{sec_uid}`.
  • You need SQLite history, default concurrency 5, retries, and disk-based incremental modes such as increase.post.
    The README's “Feature Overview” and “Key Config Fields” list SQLite history, concurrency 5, exponential backoff, and increase.post/like/mix/music.
  • You need a REST API that submits jobs and checks status with --serve --serve-port 8000.
    The README's “Run as REST API server” gives that command and lists `/api/v1/download`, `/api/v1/jobs`, and `/api/v1/health`.
  • You need browser fallback for post and can install Playwright Chromium and complete CAPTCHA manually.
    The README's “Install dependencies” and “FAQ” require playwright and Chromium and state that fallback is fully validated for post.

Skip it if you

  • You must run collect or collectmix together with post, like, mix, or music.
    The README's “Current Limitations” explicitly requires collect/collectmix to run alone.
  • You need incremental stopping with increase for favorites collections.
    The README's “Current Limitations” says increase applies only to post/like/mix/music and favorites collections do not support incremental stop.
  • Your deliverable must be a directly playable HLS recording without additional processing.
    The README's “Current Limitations” says HLS saves only the playlist and requires ffmpeg for playable output.
  • You require all live-stream scenarios to be verified and stably supported.
    The README's “Current Limitations” says the webcast room endpoint is not verified against every live scenario and is experimental.

Requirements

  • Python 3.8+, with macOS, Linux, and Windows support.
  • Run the README command pip install -r requirements.txt first.
  • Browser fallback requires playwright and Chromium: pip install playwright; python -m playwright install chromium.
  • The sample configuration uses cookies fields including ttwid, odin_tt, and passport_csrf_token.
  • Docker deployment requires the Dockerfile plus mounted config.yml and Downloaded paths.
  • Transcription requires transcript.enabled and a valid OPENAI_API_KEY or transcript.api_key; the example model is gpt-4o-mini-transcribe.

First step (verbatim from README)

pip install -r requirements.txt

Watch out

  • If only around 20 post items download, the README requires browser_fallback.enabled, headless disabled, and manual verification.
    README FAQ: “Why do I only get around 20 posts?”
  • collect and collectmix depend on the account represented by logged-in cookies and cannot target arbitrary accounts' favorite collections.
    README section: “Current Limitations”.
  • SQLite history does not decide incremental skips; disk-based skipping is controlled by increase.post/like/mix/music.
    README sections: “Feature Overview” and “Key Config Fields”.
  • image-note items do not generate transcripts; transcript applies only to video items.
    README sections: “Optional Feature: Video Transcription” and “Why are transcript files not generated?”
  • The sample sets progress.quiet_logs to true; the README specifies --show-warnings or -v for debugging.
    README sections: “Minimal Working Config” and “FAQ”.

Not stated in the README

  • The materials do not specify Douyin API behavior, cookie lifetime, or account risk-control rules.
  • The materials provide no throughput, disk-usage, or memory figures for different download scales.
  • The materials do not specify the Docker base version, Playwright Chromium version, or how to install ffmpeg.
  • The provided materials omit the Desktop App (Douzy) section, the full cookie-acquisition flow, and the disclaimer text.
  • The materials do not specify REST API authentication, concurrency limits, or production security settings.
  • The materials provide no causal evidence linking the 2026-09-14 Trending entry to the 452 new stars.

💡 Deep Analysis

6
No I only want to download `collect` and `collectmix` for the account represented by my current cookie, while running them together with `post` and relying on `increase` for incremental stopping. Does this project fit my workflow?
For: A research archivist who needs to archive favorite collections and collected mixes from the account represented by a login cookie, while expecting to use `increase` for incremental synchronization

No. This workflow is not directly supported because favorite modes have explicit account, combination, and incremental-download limitations.

  • The README says collect / collectmix work only for the account represented by the logged-in cookies; they are not general favorite-data access modes.
  • collect / collectmix must be used alone and cannot be combined with post, like, mix, or music, so they cannot be placed in the same mode configuration as post.
  • The README explicitly states that increase applies to post / like / mix / music; favorite collection modes do not support incremental stopping.
  • Although number.collect and number.collectmix exist, with 0 meaning unlimited, that does not remove the mode restrictions.

The project can archive favorites for the logged-in account, but it does not directly support a combined-mode, incremental favorite-sync workflow.

  • Current Limitations: `collect / collectmix currently work for the account represented by the logged-in cookies only`
  • Current Limitations: `collect / collectmix must be used alone and cannot be combined with post / like / mix / music`
  • Current Limitations: `increase ... favorites collection modes do not support incremental stop`
  • Key Config Fields: `number.post/like/mix/music/collect/collectmix`, with `0 = unlimited`
cp config.example.yml config.yml
Not stated in the README:The README does not specify the execution order of `collect` and `collectmix` within the same standalone task;The README does not describe recovery behavior when the cookie expires or account permissions change
No My downloads include both videos and image notes, and I plan to enable OpenAI's `gpt-4o-mini-transcribe` with TXT and JSON output. Can this project generate transcripts for both content types?
For: A Python content-processing engineer who needs automatic transcripts for downloaded videos using OpenAI's `gpt-4o-mini-transcribe` while preserving original image-note files

No. It cannot transcribe both content types because the README limits transcription to videos; image-note items do not produce transcript files.

  • The sample configuration uses model: gpt-4o-mini-transcribe and supports response_formats: ["txt", "json"].
  • The Optional Feature section explicitly says the behavior “applies to video items only”; image-note items do not generate transcripts.
  • Transcription also requires a valid OPENAI_API_KEY or transcript.api_key; the FAQ says to check transcript.enabled, whether the item is a video, and the selected response formats.
  • Transcription runs after video download, so it is a post-processing feature rather than OCR or image-text recognition for image notes.

It is suitable for speech transcription after video archiving. Image notes can still be saved with media and metadata, but the README provides no OCR support.

  • Optional Feature: `Current behavior applies to video items only (image-note items do not generate transcripts)`
  • Minimal Working Config: `model: gpt-4o-mini-transcribe`, `response_formats: ["txt", "json"]`
  • FAQ: `Why are transcript files not generated?`
  • Project insights common_pitfalls: `transcription applies only to videos, not image notes`
export OPENAI_API_KEY="sk-xxxx"
Not stated in the README:The README does not specify per-video size, duration, or concurrency limits for transcription;The README does not specify exact OpenAI API costs or the retry policy for transcription failures
No I already use FastAPI/Uvicorn and want to submit Douyin download jobs and query their status in Docker. Can this project directly serve as a multi-user, highly available download backend?
For: A Python automation engineer integrating Douyin collection into an internal system with FastAPI/Uvicorn and Docker, submitting jobs, querying status, and mounting the download directory to the host

No. It should not be used directly as a multi-user, highly available backend because the README exposes only a basic job API and local persistence, with no documented authentication, authorization, or distributed task design.

  • REST mode starts with --serve --serve-port 8000 and provides submission, single-job status, job listing, and health-check endpoints.
  • Completed jobs are pruned by max_jobs and job_ttl_seconds; the defaults are 24 hours and 500 jobs, which is more consistent with a bounded lightweight service.
  • The Docker example mounts only config.yml and Downloaded; database_path defaults to a SQLite file in the current working directory.
  • Project insights explicitly do not show multi-user support, distributed queues, object storage, permission isolation, or high availability.

It is suitable as a single-host internal service or automation entry point, but a multi-tenant deployment would need additional authentication, isolation, shared storage, and recovery mechanisms.

  • Usage: `python run.py --serve --serve-port 8000`
  • REST API: `POST /api/v1/download`, `GET /api/v1/jobs/{job_id}`, `GET /api/v1/jobs`, and `GET /api/v1/health`
  • REST API: `Finished jobs are pruned by TTL (default 24h) and max-jobs (default 500)`
  • Key Config Fields: `database_path` defaults to `dy_downloader.db` in the current working directory
  • Project insights user_experience.usage_limitations: no demonstrated multi-user, distributed queue, object storage, permission isolation, or high-availability design
pip install fastapi uvicorn       # one-time optional dep
Not stated in the README:The README does not state whether the REST API provides authentication, authorization, rate limiting, or tenant isolation;The README does not describe concurrent behavior when multiple containers or processes share SQLite and the Downloaded directory
No I plan to record Douyin live streams for long periods in Docker and require both FLV and HLS sources to produce playable video files directly. Can this project serve as a stable live recorder?
For: A Linux operations engineer who needs to record Douyin live streams in Docker, preserve FLV output, and process HLS live sources into playable files

No. It should not be treated as a stable general-purpose live recorder because the README labels live recording experimental and says HLS normally saves only a playlist.

  • Current Limitations states that live recording saves FLV natively, while HLS sources save only the playlist and require ffmpeg for playable output.
  • The same section says the webcast room endpoint has not been verified against every live scenario and should be treated as experimental.
  • live.* exposes max_duration_seconds, chunk_size, and idle_timeout_seconds, showing that recording controls exist, but not that every stream source is covered.
  • Project insights also identify unverified live scenarios and post-processing requirements for FLV/HLS.

It can be used as an experimental collector in controlled cases. For directly playable HLS output, unattended long-running operation, and reliable coverage of all live types, the README does not provide sufficient evidence.

  • Current Limitations: `Live stream recording saves FLV natively; HLS sources only save the playlist (use ffmpeg for playable output)`
  • Current Limitations: `The webcast room endpoint is not verified against every live scenario — treat as experimental`
  • Key Config Fields: `live.*` includes `max_duration_seconds / chunk_size / idle_timeout_seconds`
  • Project insights usage_limitations: `live recording is experimental`
docker build -t douyin-downloader .
Not stated in the README:The README does not state whether ffmpeg is preinstalled in the Docker image;The README does not describe automatic reconnection, file remuxing, or long-term disk-growth control after live-stream interruptions
It depends I need to batch-download a creator's post items on Windows with Python 3.8+, logged-in cookies, and the default concurrency of five. If I normally receive only about 20 posts, can this project provide a reasonably complete archive?
For: A content archivist who needs to batch-archive Douyin creator posts on Linux, macOS, or Windows using a Python configuration file, SQLite history, and browser fallback for pagination limits

It depends: the project is suitable for batch post archiving, but completeness depends on browser fallback, valid login state, and manual CAPTCHA handling.

  • The README explicitly supports post; number.post: 0 means unlimited, while the sample configuration includes thread: 5, retry_times: 3, and SQLite history.
  • For receiving only about 20 posts, the README attributes this to pagination risk control and requires browser_fallback.enabled: true, headless: false, manual verification in the browser popup, and keeping the popup open long enough.
  • Browser fallback is “fully validated for post”, giving this mode stronger support than like, mix, or music.

This is not an official export tool; the README does not promise complete results for every account, CAPTCHA state, or page change.

  • Minimal Working Config: `thread: 5`, `retry_times: 3`, `browser_fallback.enabled: true`, `headless: false`
  • FAQ: `Why do I only get around 20 posts?`
  • Current Limitations: `Browser fallback is fully validated for post`
  • Quick Start: `Python 3.8+`, `macOS / Linux / Windows`
pip install -r requirements.txt
Not stated in the README:The README does not state the actual completion rate for different accounts after pagination risk control is triggered;The README does not specify cookie lifetime or automatic renewal behavior
Yes I need to batch-download videos, image notes, collections, and music through an HTTP/HTTPS proxy, while avoiding overwriting files already on disk after an interrupted job. Does this project cover these download-control requirements?
For: A Python command-line user archiving videos, image notes, collections, and music in a restricted network environment, using an HTTP/HTTPS proxy, retries, and disk-based incremental downloads

Yes. These requirements fit the project’s configuration-driven download, retry, proxy, and disk-based incremental capabilities.

  • mode supports post, like, mix, and music; the project description also explicitly lists videos, image notes, and collections.
  • The optional proxy field supports HTTP/HTTPS proxies, while retry_times controls retries; the sample configuration sets retry_times: 3.
  • With increase.post/like/mix/music: true, existing primary media on disk is skipped; false causes downloads to be redone and overwritten for the current scope.
  • The README also provides download integrity checks. Project insights state that checks such as Content-Length are used and incomplete files are removed on failure; SQLite records history, but skipping depends on correctly configuring increase.

It is suitable for recoverable downloads on a single host or a Docker-mounted directory. The README does not guarantee proxy availability, immunity to platform throttling, or a watermark-free source for every item.

  • Key Config Fields: `mode` supports `post`/`like`/`mix`/`music`
  • Key Config Fields: `proxy`, `database`, `thread`, and `retry_times`
  • Key Config Fields: `increase... true: skip existing primary media on disk`
  • Feature Overview: `retries, SQLite deduplication, download integrity checks`
  • Project insights common_pitfalls: `SQLite history alone does not determine incremental skipping`
python run.py -c config.yml
Not stated in the README:The README does not specify proxy authentication syntax, proxy pools, or proxy failover;The README does not explain integrity-check behavior when Content-Length is missing or the media server uses chunked responses

✨ Highlights

  • Supports videos, image-notes, collections, music, and profile batch downloads
  • SQLite records download history and supports deduplication and incremental downloads
  • Playwright browser fallback handles pagination restrictions for post mode
  • Uses default concurrency 5, 1s/2s/5s backoff, and integrity checks
  • Live recording saves FLV natively, while HLS saves only the playlist

🔧 Engineering

  • Uses run.py -c config.yml to batch-download post, like, mix, and music modes.
  • Provides a --serve --serve-port 8000 REST API with job status and health endpoints.
  • Optionally uses OpenAI gpt-4o-mini-transcribe to generate txt or json transcripts for videos.

⚠️ Risks

  • collect and collectmix work only for the account in logged-in cookies and cannot be combined with post and other modes.
  • Browser fallback is fully validated only for post; like, mix, and music still rely on API pagination.
  • The webcast room endpoint is not verified for every live scenario and is marked experimental.
  • HLS live streams save only the playlist; ffmpeg is needed for playable output.

👥 For who?

  • Developers needing to batch-archive Douyin videos, image-notes, or collections on Python 3.8+.
  • Script users needing SQLite history and disk-based skipping through increase.post and related modes.
  • Teams wanting download job APIs with FastAPI/uvicorn or deployment through the included Dockerfile.