This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
# Build
go build ./cmd/vget
# Build to specific directory
go build -o build/vget ./cmd/vget
# Run directly
go run ./cmd/vget
# Build with version info (for releases)
go build -ldflags "-X github.com/guiyumin/vget/internal/version.Version=1.0.0" ./cmd/vgetvget is a media downloader CLI built with Go. It uses Cobra for command parsing and Bubbletea for interactive TUI elements (spinners, progress bars).
- CLI Layer (
internal/cli/) - Cobra commands parse flags and dispatch to handlers - Extractor Layer (
internal/extractor/) - URL matching and media metadata extraction - Downloader Layer (
internal/downloader/) - HTTP download with Bubbletea progress TUI
The MediaType enum in internal/extractor/extractor.go defines supported media types:
MediaTypeVideo- Video files (Twitter, YouTube, etc.)MediaTypeAudio- Audio files (podcasts)MediaTypePDF- PDF documentsMediaTypeEPUB- EPUB ebooksMediaTypeMOBI- MOBI ebooksMediaTypeAZW- AZW ebooksMediaTypeUnknown- Fallback (treated as video)
Each type has specific terminal output formatting in internal/cli/extract.go.
To add support for a new site, implement the Extractor interface in internal/extractor/:
type Extractor interface {
Name() string
Match(url string) bool
Extract(url string) (*VideoInfo, error)
}Set the appropriate MediaType in the returned VideoInfo:
return &VideoInfo{
ID: "...",
Title: "...",
MediaType: MediaTypeAudio, // or MediaTypeVideo, etc.
Formats: []Format{...},
}, nilExtractors are auto-registered via init() functions. See xiaoyuzhou.go or twitter.go for examples.
vget <url>- Download media from URLvget init- Interactive config wizard (TUI)vget update- Self-update to latest versionvget search --podcast <query>- Search Xiaoyuzhou podcastsvget ls <remote>:<path>- List WebDAV remote directoryvget config show- Show current configurationvget config set <key> <value>- Set config value (non-interactive)vget config get <key>- Get config valuevget config webdav ...- Manage WebDAV servers
Translations are embedded YAML files in internal/i18n/locales/. Supported: en, zh, jp, kr, es, fr, de.
Access translations via i18n.T(langCode) which returns a *Translations struct with typed fields.
User config lives in ~/.config/vget/config.yml. Two ways to configure:
- Interactive (TUI):
vget init- Bubbletea wizard for first-time setup - Non-interactive:
vget config set <key> <value>- For scripting/Docker
Supported keys for vget config set:
language- Language code (en, zh, jp, kr, es, fr, de)output_dir- Default download directoryformat- Preferred format (mp4, webm, best)quality- Default quality (1080p, 720p, best)twitter.auth_token- Twitter auth for NSFW content
IMPORTANT: Config is read fresh on every command execution (not cached at startup). This is intentional and MUST be preserved:
- Enables config changes without restart
- Critical for Docker UX (no container restart needed)
- Never change this behavior
The XHS extractor (internal/extractor/xiaohongshu.go) uses browser automation:
- Browser: Rod's auto-downloaded Chromium (NOT system Chrome)
- Binary location:
~/.cache/rod/browser/ - User data:
~/.config/vget/browser/(persistent, shared by all extractors) - Stealth: Uses
go-rod/stealthfor anti-bot detection
Important: Never use system Chrome profiles with browser automation - it can corrupt session data.
internal/updater/ uses go-selfupdate to fetch releases from GitHub (guiyumin/vget). Version is set in internal/version/version.go.
- BUILD OUTPUT DIRECTORY IS ./build
- YOU ONLY BUILD IT. I WILL TEST IT BY MYSELF.