📝 LLM & AI

Typer: CLI Applications Without the Boilerplate

P
Author
Pyland
📅
Published
30.06.2026
⏱️
Reading time
1 min
👁️
Views
88
🌿
Level
Medium

Typer builds CLIs from Python type annotations. No argparse, no manual parsing — just decorators and types.

Installation

uv add typer

Basic application

import typer

app = typer.Typer()

@app.command()
def greet(name: str, times: int = 1):
    """Greets the user."""
    for _ in range(times):
        typer.echo(f"Hello, {name}!")

if __name__ == "__main__":
    app()
uv run python main.py Alice          # Hello, Alice!
uv run python main.py Alice --times 3  # Three times
uv run python main.py --help         # Auto-generated docs

Multiple commands

import typer

app = typer.Typer(help="AI agent CLI")

@app.command()
def chat(message: str = typer.Argument(..., help="Message for Claude")):
    """Send a message to Claude."""
    typer.echo(f"Sending: {message}")

@app.command()
def history(limit: int = typer.Option(10, help="Number of messages")):
    """Show conversation history."""
    typer.echo(f"Last {limit} messages")

@app.command()
def clear():
    """Clear the history."""
    typer.echo("History cleared")

if __name__ == "__main__":
    app()
uv run python main.py chat "Hello!"
uv run python main.py history --limit 5
uv run python main.py clear

Argument vs Option

@app.command()
def analyze(
    text: str = typer.Argument(...),           # required positional
    model: str = typer.Option("claude-sonnet-4-6"),  # --model
    verbose: bool = typer.Option(False, "--verbose", "-v"),  # flag
):
    pass
  • Argument(...) — positional, required
  • Argument("default") — positional with a default value
  • Option(default) — named --param value

Colors and formatting

from rich.console import Console

console = Console()

@app.command()
def status():
    console.print("[bold green]✓[/] Agent running")
    console.print("[bold red]✗[/] Connection error")
    typer.echo(typer.style("Done", fg=typer.colors.GREEN, bold=True))

Interactive input

@app.command()
def setup():
    api_key = typer.prompt("Enter your API key", hide_input=True)
    confirm = typer.confirm("Save to .env?")
    if confirm:
        typer.echo("Saved!")

Your reaction to the article

💬 Comments (0)

🔐 Sign in to leave a comment
🚪 Login
💭

No comments yet

Be the first to share your opinion about this article!

🔗 Similar

Similar articles

Continue learning with these materials

📝

httpx: A Modern HTTP Client for Python

httpx is a next-generation HTTP client. Its interface is similar to requests, but it supports...

📅 30.06.2026 👁️ 108
📝

AI Agents: ReAct Loop and Autonomous Actions

A chatbot answers questions. An agent takes action: it calls tools, retrieves real data, and...

📅 30.06.2026 👁️ 100
📝

Document Chunking Strategies for RAG

Embedding a long document averages out its meanings — a specific question won't find the...

📅 30.06.2026 👁️ 100

Did you like the article?

Subscribe to our updates and receive new articles first. Grow with PyLand!