suno-cli
Generate AI music from your terminal — full Suno v5.5 support
A 3.4MB Rust binary that talks directly to Suno's API. Generate songs with custom lyrics, style tags, vocal control, weirdness/style sliders, and every v5.5 feature — no browser needed.
Install | Quick Start | Commands | Features | Contributing
Why
Suno has no official API. The web UI works, but you can't script it, pipe lyrics from a file, batch-generate, or integrate it into a music production workflow.
This CLI fixes that. Cookie-based auth, every generation parameter exposed as a flag, dual JSON/table output for both humans and AI agents.
Install
Homebrew (macOS/Linux)
Cargo (any platform)
Pre-built binaries
Download from GitHub Releases — binaries for macOS (Apple Silicon + Intel), Linux (x86_64 + ARM), and Windows.
Quick Start
# 1. Get your JWT from browser DevTools (Network tab → any Suno request → Authorization header)
# 2. Check your credits
# 3. Generate lyrics (free, no credits)
# 4. Generate a song
Commands
suno generate Custom mode — lyrics + tags + title + sliders
suno inspire Description mode — Suno writes lyrics from your prompt
suno lyrics Generate lyrics only (free, no credits)
suno extend Continue a clip from a timestamp
suno concat Stitch clips into a full song
suno cover Create a cover with different style
suno remaster Remaster with a different model
suno stems Extract vocals and instruments
suno feed List your songs
suno status <id> Check generation progress
suno download <id> Download audio/video
suno credits Show balance and plan info
suno models List available models with limits
suno auth Set up authentication
suno config show | set | check
suno agent-info Machine-readable capabilities JSON
Features
Generation Parameters
| Flag | What it does | Values |
|---|---|---|
--title |
Song title | up to 100 chars |
--tags |
Style direction | "pop, synths, upbeat" (1000 chars) |
--exclude |
Styles to avoid | "metal, heavy, dark" (1000 chars) |
--lyrics / --lyrics-file |
Custom lyrics with [Verse] tags |
up to 5000 chars |
--prompt (inspire) |
Free text description | up to 500 chars |
--model |
Model version | v5.5, v5, v4.5+, v4.5, v4, v3.5, v3, v2 |
--vocal |
Vocal gender | male, female |
--weirdness |
How experimental | 0-100 |
--style-influence |
How strictly to follow tags | 0-100 |
--variation |
Output variation | high, normal, subtle |
--instrumental |
No vocals | flag |
--wait |
Block until done | flag |
--download <dir> |
Auto-download after generation | directory path |
Models
| Version | Codename | Default | Max Lyrics |
|---|---|---|---|
| v5.5 | chirp-fenix | Yes | 5000 chars |
| v5 | chirp-crow | 5000 chars | |
| v4.5+ | chirp-bluejay | 5000 chars | |
| v4.5 | chirp-auk | 5000 chars | |
| v4 | chirp-v4 | 3000 chars |
Agent-Friendly
Every command supports --json for structured output. When stdout is piped, JSON is auto-detected. Progress, errors, and spinners go to stderr. Exit codes are semantic:
| Code | Meaning |
|---|---|
| 0 | Success |
| 1 | Runtime error |
| 2 | Config error |
| 3 | Auth error |
| 4 | Rate limited |
# Pipe-friendly: auto-JSON when piped
|
# Explicit JSON
How Auth Works
Browser DevTools → copy JWT + device-id → suno auth → stored at ~/.config/suno-cli/auth.json
The JWT expires after ~1 hour. Re-run suno auth with a fresh token when it expires. The CLI checks expiry before every request and tells you when it's time to refresh.
Project Structure
src/
├── main.rs Entry point, command routing
├── cli.rs All clap derive structs
├── auth.rs JWT storage, browser-token generation
├── config.rs Config layering (env vars, defaults)
├── errors.rs Error types with exit codes
├── download.rs Audio/video download with progress bar
├── api/
│ ├── mod.rs SunoClient — auth headers, base requests
│ ├── types.rs Clip, Model, BillingInfo, etc.
│ ├── generate.rs Music generation + polling
│ ├── lyrics.rs Lyrics generation
│ ├── billing.rs Credits and plan info
│ ├── feed.rs Song listing
│ ├── concat.rs Clip concatenation
│ ├── cover.rs Cover generation
│ ├── remaster.rs Remastering
│ └── stems.rs Stem extraction
└── output/
├── mod.rs Format detection (TTY vs piped)
├── json.rs JSON envelope
└── table.rs Terminal tables
Contributing
- Fork the repo
- Create a branch (
git checkout -b feature/your-idea) - Make your changes and test with
cargo test - Open a PR
We especially welcome:
- New API endpoint coverage (personas, voices, custom models)
- Better auth flows (Clerk cookie refresh, OS keychain)
- Integration tests
License
MIT — see LICENSE.
Built by Boris Djordjevic at Paperfoot AI
If this saves you time: