Are you an LLM? Read llms.txt for a summary of the docs, or llms-full.txt for the full context.
Skip to content

Configuration

zo uses a TOML configuration file for settings, custom models, and personalization.

Config File Location

  • Linux/macOS: ~/.config/zo/config.toml

Quick Setup

Initialize Config

zo +init-config

This creates ~/.config/zo/config.toml with:

  • Helpful comments explaining all options
  • Example custom models
  • List of available themes
  • Color customization examples

Basic Configuration

# API Key (alternatively use OPENROUTER_API_KEY env var)
api_key = "sk-or-v1-..."
 
# Default model (uses fuzzy matching)
default_model = "flash"

Complete Configuration Example

# ~/.config/zo/config.toml
 
# API Key (alternatively set OPENROUTER_API_KEY environment variable)
api_key = "sk-or-v1-..."
 
# Default model when no model specified
# Uses fuzzy matching - can be "sonnet", "flash", "gpt4", etc.
default_model = "flash"
 
# Syntax highlighting theme for code blocks
# See available themes below
theme = "base16-ocean.dark"
 
# Custom colors for inline markdown elements
[inline_colors]
heading = "cyan"        # Color for # Headers
inline_code = "yellow"  # Color for `code`
emphasis = "white"      # Color for *italic* and **bold**
 
# Define custom models with system prompts
[[custom_models]]
name = "coder"
model = "anthropic/claude-sonnet-4.5"
system_prompt = "You are an expert programmer. Provide concise, well-commented code with error handling. Follow best practices and explain your choices."
 
[[custom_models]]
name = "reviewer"
model = "anthropic/claude-sonnet-4.5"
system_prompt = "You are a senior code reviewer. Focus on: bugs, performance, security, readability, and best practices. Be thorough but constructive."
 
[[custom_models]]
name = "writer"
model = "openai/gpt-4o"
system_prompt = "You are a professional technical writer. Write clear, engaging documentation. Use examples, avoid jargon, and structure content logically."

Configuration Fields

API Key

Field: api_key
Type: String (optional)
Default: None

api_key = "sk-or-v1-your-key-here"

Alternative: Environment variable (recommended)

export OPENROUTER_API_KEY="sk-or-v1-your-key-here"

Priority: Environment variable takes precedence over config file.

Default Model

Field: default_model
Type: String (optional)
Default: "flash" (Google Gemini Flash)

default_model = "sonnet"

Uses fuzzy matching - accepts any model name that matches built-in or custom models.

Theme

Field: theme
Type: String (optional)
Default: "base16-ocean.dark"

theme = "Monokai Extended"
Available Themes: Dark Themes:
  • base16-ocean.dark (default)
  • Solarized-dark
  • Monokai Extended
  • Nord
  • Dracula
  • One Dark
  • Zenburn
Light Themes:
  • base16-ocean.light
  • InspiredGitHub
  • Solarized-light
  • One Light

Inline Colors

Section: [inline_colors]
Type: Object (optional)
Fields: heading, inline_code, emphasis

[inline_colors]
heading = "cyan"
inline_code = "yellow"
emphasis = "white"
Named Colors:
  • black, red, green, yellow
  • blue, magenta, cyan, white
  • gray, darkgray
  • lightred, lightgreen, lightyellow
  • lightblue, lightmagenta, lightcyan
Hex Colors:
[inline_colors]
heading = "#00FFFF"
inline_code = "#FFFF00"
emphasis = "#FFFFFF"

Smart Defaults: zo automatically chooses colors based on your theme:

  • Dark themes → Bright colors
  • Light themes → Dark colors

Custom Models

Section: [[custom_models]]
Type: Array of objects

[[custom_models]]
name = "model_name"
model = "provider/model-id"
system_prompt = "Optional system prompt"
Fields:
  • name (required) - Short name for fuzzy matching
  • model (required) - Full OpenRouter model ID
  • system_prompt (optional) - System prompt applied to all requests
Examples:
# Specialized coder
[[custom_models]]
name = "coder"
model = "anthropic/claude-sonnet-4.5"
system_prompt = "Expert programmer. Provide well-commented, tested code following best practices."
 
# Security analyst
[[custom_models]]
name = "security"
model = "anthropic/claude-opus-4.5"
system_prompt = "Security expert. Analyze for vulnerabilities, attack vectors, and provide mitigation strategies."
 
# Quick alias (no system prompt)
[[custom_models]]
name = "fast"
model = "google/gemini-2.5-flash"

Environment Variables

OPENROUTER_API_KEY

Required: Yes (either this or api_key in config)

export OPENROUTER_API_KEY="sk-or-v1-..."
Recommended approach:
# Add to ~/.bashrc or ~/.zshrc
echo 'export OPENROUTER_API_KEY="sk-or-v1-..."' >> ~/.bashrc
source ~/.bashrc

Configuration Examples

Minimal Setup

# Just the essentials
api_key = "sk-or-v1-..."

Recommended Setup

# API key via environment variable
# default_model uses fuzzy matching
default_model = "sonnet"
 
# Dark theme optimized
theme = "base16-ocean.dark"
 
# One custom model for coding
[[custom_models]]
name = "coder"
model = "anthropic/claude-sonnet-4.5"
system_prompt = "Expert programmer. Provide clean, well-documented code."

Power User Setup

default_model = "flash"
theme = "Monokai Extended"
 
[inline_colors]
heading = "#61AFEF"
inline_code = "#E5C07B"
emphasis = "#ABB2BF"
 
# Multiple specialized models
[[custom_models]]
name = "coder"
model = "anthropic/claude-sonnet-4.5"
system_prompt = "Expert programmer focusing on clean, tested code."
 
[[custom_models]]
name = "reviewer"
model = "anthropic/claude-sonnet-4.5"
system_prompt = "Senior code reviewer. Flag bugs, security issues, and performance problems."
 
[[custom_models]]
name = "architect"
model = "anthropic/claude-opus-4.5"
system_prompt = "Software architect. Consider scalability, maintainability, and tradeoffs."
 
[[custom_models]]
name = "writer"
model = "openai/gpt-4o"
system_prompt = "Technical writer. Create clear, comprehensive documentation."
 
[[custom_models]]
name = "debugger"
model = "openai/gpt-4o"
system_prompt = "Debugging expert. Analyze errors systematically and provide root cause analysis."

Validation

zo validates your config on load and provides helpful error messages.

Common Validation Errors

Empty Custom Model Name:
Error: Custom model name cannot be empty
Duplicate Model Names:
Error: Duplicate custom model name: 'coder'
Invalid Theme:
Error: Theme 'invalid-theme' not found.
Available themes: base16-ocean.dark, Solarized-dark, ...

Best Practices

API Key Security

# ✅ Use environment variable
export OPENROUTER_API_KEY="..."
 
# ✅ Restrict config file permissions
chmod 600 ~/.config/zo/config.toml
 
# ❌ Don't commit to git
echo "config.toml" >> .gitignore

Model Organization

Group custom models by use case:

# Code-related
[[custom_models]]
name = "coder"
# ...
 
[[custom_models]]
name = "reviewer"
# ...
 
# Writing-related
[[custom_models]]
name = "writer"
# ...
 
[[custom_models]]
name = "docs"
# ...

System Prompt Tips

# ✅ Good - specific and actionable
system_prompt = "You are a Rust expert. Provide idiomatic code with error handling, documentation, and tests."
 
# ❌ Too vague
system_prompt = "You are helpful."

Troubleshooting

Config Not Found

# Create default config
zo +init-config
 
# Verify location
ls -la ~/.config/zo/config.toml

API Key Not Working

# Check environment variable
echo $OPENROUTER_API_KEY
 
# Check config file
cat ~/.config/zo/config.toml | grep api_key

Theme Not Working

# Initialize config to see available themes
zo +init-config
 
# Check your theme name exactly matches
# Theme names are case-sensitive

Custom Model Not Found

# List all models (including custom)
zo +list-models
 
# Verify your custom model appears in the list

Next Steps