douyin

A command line for Douyin (抖音). douyin reads public Douyin data and prints
clean, pipeable records. One pure-Go binary, no API key, no login.
Install • Commands • Usage • Anti-bot • Serve • Docs

douyin reads the same public web surface a logged-out browser sees: the open
iesdouyin hot-search billboards, and the www.douyin.com/aweme/v1/web/*
endpoints the page's own JavaScript calls, signed the way the web client signs
them. It returns records as a table, JSON, JSONL, CSV, TSV, or URLs, and serves
the same read operations over HTTP and MCP. Output is a table at a terminal and
JSONL when piped, so douyin hot | jq works with no flags.
douyin is an independent tool. It is not affiliated with, authorized, or
endorsed by ByteDance or Douyin.
Install
go install github.com/tamnd/douyin-cli/cmd/douyin@latest
Or with Homebrew:
brew install tamnd/tap/douyin
Or grab a prebuilt binary from the releases,
or run the container image:
docker run --rm ghcr.io/tamnd/douyin:latest hot
Shell completion is built in: douyin completion bash|zsh|fish|powershell.
Commands
Read operations work from the CLI, over HTTP (douyin serve), and over MCP
(douyin mcp).
| Command |
Description |
hot |
Hot-search billboard, in rank order (--tab realtime|video|music|star) |
video <url|id> |
One video record |
user <sec_uid|url> |
Profile record for a sec_uid |
posts <sec_uid|url> |
A user's public videos |
comments <url|id> |
Comments under a video |
search <query> |
Mixed search hits (videos and users) |
| Command |
Description |
serve |
Serve the read operations over HTTP (NDJSON) |
mcp |
Run as an MCP server over stdio |
raw <url> |
Fetch a URL and print its body untouched |
version |
Print version information |
Usage
douyin hot # realtime hot-search board, in rank order
douyin hot --tab video -n 10 # top 10 hot videos
douyin hot --fields rank,word,hot_value # pick the columns
douyin video 7400000000000000000 # one video record
douyin search 美食 -n 20 # search hits
douyin hot -o json # JSON output
douyin hot | jq # JSONL piped to jq
Output is a table when you are at a terminal and JSONL when you pipe, so the
last line works with no flags. Every command takes the same global flags
(-o/--output, --fields, -n/--limit, --rate, --timeout, and more); see
the CLI reference for the full
surface.
Anti-bot
Douyin serves some surfaces openly and walls the rest behind its web anti-bot
system. The tool is honest about this: it recognises each block signal and exits
cleanly rather than emitting a challenge page or faking data.
- Open anywhere, no key:
hot (the hot-search billboard).
- Walled behind the web anti-bot challenge:
video, user, posts,
comments, and search. These call the signed www.douyin.com/aweme/v1/web/*
API with a reimplemented a_bogus signature and a fresh msToken. From a
datacenter or non-China IP, Douyin answers the signed call with an empty body
or an __ac challenge shell; the command detects this and exits with code 4
(needs a residential session). The signing and parsers are correct and serve
from a China IP or a warm browser session. The wall is at the IP and session
layer, so no key the client could send opens it.
Serve it
The read operations are also an HTTP API and an MCP server, backed by the same
code as the CLI.
douyin serve # HTTP on :8080, NDJSON; /healthz and /v1/openapi.json
douyin mcp # MCP server over stdio
Docs
Full documentation lives at douyin-cli.tamnd.com.
License
Apache-2.0. See LICENSE. douyin is an independent tool and is not
affiliated with ByteDance or Douyin.