Unified AI platform for terminal, gRPC server, and Kubernetes.
15 providers · 14 autonomous agents · 7-pattern quality pipeline · one binary.
Português • Full documentation • Architecture • Observability
ChatCLI connects the industry's leading LLMs to a single, extensible interface — from
chatcli -pin your terminal to a Kubernetes operator with an autonomous AIOps pipeline, passing through a production-ready gRPC server with authentication, failover, and Prometheus metrics.
| Multi-provider with failover | 15 LLM providers (OpenAI · OpenAI Responses · Anthropic · Bedrock · Google · xAI · ZAI · MiniMax · Moonshot (Kimi) · Copilot · GitHub Models · StackSpot · OpenRouter · Ollama · Devin CLI) with intelligent error classification, exponential backoff, and per-provider cooldown. The Devin provider wraps the local Devin CLI as an LLM transport — no undocumented Cognition APIs, full ChatCLI harness and headroom on top. |
| Autonomous agents | 14 built-in workers coordinated by a ReAct engine (Reason + Act): 12 orchestration specialists run in parallel + 2 quality agents (refiner, verifier), plus a 7-pattern quality pipeline. |
| Quality pipeline | Self-Refine, Chain-of-Verification (CoVe), Reflexion, RAG + HyDE, Plan-and-Solve (ReWOO), cross-provider reasoning backbone — all composed via a thread-safe state machine with circuit breakers and hot reload. |
| Scheduler (Chronos) | Durable scheduling with cron + wait-until + DAG + daemon mode. /schedule, /wait, /jobs + @scheduler tool for agents. CRC32 WAL, snapshots, rate limiter, circuit breakers, JSONL audit, 13 Prometheus metrics. Jobs survive crashes and CLI exit. |
| Durable Reflexion | WAL-backed queue with worker pool, dead letter queue, boot replay, exponential retry with jitter — lessons survive process crashes. |
| Semantic convergence | char → Jaccard → embedding cosine cascade for Self-Refine, with LRU/TTL cache and quality regression detection. |
| Production-ready | gRPC + TLS 1.3, JWT + RBAC, AES-256-GCM, rate limiting, audit logging, 50+ Prometheus metrics. |
| Kubernetes-native | Operator with 17 CRDs and an autonomous AIOps pipeline (54+ remediation actions), SLO monitoring, post-mortems. |
| Extensible | Plugins with Ed25519 signature verification, multi-registry skills (skills.sh, ClawHub, ChatCLI.dev), slash-command templates with 9-CLI interop (Claude Code, Devin, Gemini, Codex, …), lifecycle hooks, MCP client (stdio, SSE, HTTP + OAuth). |
# Homebrew (macOS / Linux)
brew tap diillson/chatcli && brew install chatcli
# Go install
go install github.com/diillson/chatcli@latest
# Pre-built, cosign-signed binaries
# https://github.com/diillson/chatcli/releasesOnce installed, ChatCLI keeps itself current: /update upgrades through the
same channel you installed with (Homebrew, go install, or verified binary
self-replace for release downloads), and CHATCLI_AUTO_UPDATE=auto stages
updates silently in the background — the next start opens on the new version.
Docker images and source builds are never touched; they get instructions
instead. See /config update for the current policy and detected channel.
For scripts and automation there is a one-shot surface: chatcli update
applies the same flow without entering the REPL, and chatcli update check
only reports. Exit codes: 0 updated or already current, 1 check/apply
failure or a manual channel with a pending update, 2 invalid usage.
Build from source
git clone https://github.com/diillson/chatcli.git && cd chatcli
go mod tidy && go build -o chatcli
# With version metadata injected via ldflags
VERSION=$(git describe --tags --always --dirty 2>/dev/null || echo "dev")
go build -ldflags "-X github.com/diillson/chatcli/version.Version=${VERSION}" -o chatcliLLM_PROVIDER=OPENAI # OPENAI, CLAUDEAI, BEDROCK, GOOGLEAI, XAI, ZAI, MINIMAX, MOONSHOT,
# COPILOT, GITHUB_MODELS, OLLAMA, STACKSPOT, OPENROUTER
OPENAI_API_KEY=sk-xxxFull provider configuration reference
| Provider | API Key | Model | Extras |
|---|---|---|---|
| OpenAI | OPENAI_API_KEY |
OPENAI_MODEL |
OPENAI_MAX_TOKENS, OPENAI_USE_RESPONSES, OPENAI_API_URL |
| Anthropic | ANTHROPIC_API_KEY |
ANTHROPIC_MODEL |
ANTHROPIC_MAX_TOKENS |
| AWS Bedrock | IAM / SSO / aws login / credentials chain |
BEDROCK_MODEL |
BEDROCK_PROFILE or AWS_PROFILE, BEDROCK_REGION or AWS_REGION, BEDROCK_CROSS_REGION |
| Google Gemini | GOOGLEAI_API_KEY |
GOOGLEAI_MODEL |
GOOGLEAI_MAX_TOKENS |
| xAI | XAI_API_KEY |
XAI_MODEL |
XAI_MAX_TOKENS |
| ZAI | ZAI_API_KEY |
ZAI_MODEL |
ZAI_MAX_TOKENS, ZAI_USE_CODING_PLAN, ZAI_THINKING, ZAI_API_URL |
| MiniMax | MINIMAX_API_KEY |
MINIMAX_MODEL |
MINIMAX_MAX_TOKENS |
| Moonshot (Kimi) | MOONSHOT_API_KEY |
MOONSHOT_MODEL |
MOONSHOT_MAX_TOKENS, MOONSHOT_THINKING |
| GitHub Copilot | GITHUB_COPILOT_TOKEN |
COPILOT_MODEL |
or /auth login github-copilot |
| GitHub Models | GITHUB_TOKEN |
GITHUB_MODELS_MODEL |
GH_TOKEN, GITHUB_MODELS_TOKEN |
| StackSpot | CLIENT_ID, CLIENT_KEY |
— | STACKSPOT_REALM, STACKSPOT_AGENT_ID |
| OpenRouter | OPENROUTER_API_KEY |
— | OPENROUTER_MAX_TOKENS, OPENROUTER_FALLBACK_MODELS, OPENROUTER_API_URL |
| Ollama | — | OLLAMA_MODEL |
OLLAMA_ENABLED=true, OLLAMA_BASE_URL |
| OpenAI (Responses API) | OPENAI_API_KEY |
OPENAI_MODEL |
OPENAI_RESPONSES_API_URL |
ChatCLI looks for its environment file in this order, and the first file that exists wins:
$CHATCLI_DOTENV(explicit; honored even when missing, so a typo is reported instead of silently ignored)./.env— the working directory~/.chatcli/.env~/.env
The home fallbacks matter for the non-interactive surfaces: an editor spawning chatcli acp, or an MCP client spawning chatcli mcp-server, does not run your shell profile — CHATCLI_DOTENV and any variable you export from .zshrc/.bashrc never reach the child process, and its working directory is the project, which usually has no .env. Before this fallback existed those servers ran with no environment file at all: providers keyed by an env var disappeared and AWS_PROFILE went missing, so Bedrock authenticated as the default profile instead of the account you logged into. Keep your file at ~/.chatcli/.env (or ~/.env) and every surface agrees. /config shows the file in effect, its origin, and the effective AWS profile.
Per-project settings: the ACP server also layers the .env of the project the editor opened (session/new's cwd) on top, fill-only — it can add variables you have not set, never override one already in effect, and only the first project announced applies. Because a project directory is untrusted input, CHATCLI_PROJECT_ENV=safe (the default) refuses credential and endpoint variables (*_API_KEY, *_TOKEN, *_BASE_URL, *_API_URL, …) from that file; all accepts everything, off disables the overlay.
OPENAI_API_URLoverrides the OpenAI chat completions endpoint. It must be the full chat completions URL (e.g.https://gateway.example.com/v1/chat/completions) — the/modelslisting URL is derived from it.- Authentication is unchanged: requests carry
Authorization: Bearer $OPENAI_API_KEY, so when redirecting to a gateway setOPENAI_API_KEYto the gateway's key. Do not combine a third-party URL with an OAuth login (/auth login openai) — the OAuth token would be sent to the gateway. OPENAI_RESPONSES_API_URLoverrides the Responses API endpoint. A customOPENAI_API_URL(different host) forces the chat completions surface — the catalog preference for the Responses API (e.g.gpt-5.4, the default) only applies on the official host, so a gateway key is never sent toapi.openai.com. Effective precedence: OAuth >OPENAI_USE_RESPONSES=true> customOPENAI_API_URLhost (chat completions) > model catalog preference >OPENAI_USE_RESPONSES=false. If your gateway does expose the Responses API, opt in withOPENAI_USE_RESPONSES=trueand setOPENAI_RESPONSES_API_URLtoo.- When the endpoint URL points to a custom host, the model listing is not filtered by model family — every model the gateway returns on
/modelsappears in the autocomplete and/switch --model. Against the official endpoint, the listing keeps only chat-capable families (hiding embeddings, whisper, tts, dall-e, moderation). The same rule applies toZAI_API_URL,MOONSHOT_API_URLandMINIMAX_API_URL. - To use a third-party OpenAI-compatible gateway as a provider separate from OpenAI (including in the server fallback chain), point the OpenRouter preset at it:
LLM_PROVIDER=OPENROUTERwithOPENROUTER_API_KEYandOPENROUTER_API_URL=https://gateway.example.com/v1/chat/completions.
ZAI_USE_CODING_PLAN=truepoints the ZAI provider at the subscription endpoint (https://api.z.ai/api/coding/paas/v4/chat/completions). The same platform API key works on both endpoints — the/coding/path is what makes requests draw from the plan instead of pay-as-you-go credits.- The plan serves
glm-5.3andglm-5.3-flash; requests for older GLM ids are routed to them server-side./costreports these calls at $0: usage is covered by the subscription, not billed per token. - An explicit
ZAI_API_URLalways wins over the toggle — set it to the full chat completions URL (e.g. the mainland endpointhttps://open.bigmodel.cn/api/coding/paas/v4/chat/completions). Any URL with an/api/coding/path is treated as plan usage. ZAI_THINKING=enabled|disabledcontrols the GLM thinking mode on both the plain and tool-calling paths (unset keeps the backend default;enabledalso preserves interleaved reasoning across turns).
|
AI-powered terminal with a Bubble Tea TUI, project context, tool calling, and autonomous agents. chatcli
chatcli -p "Explain this repo"
git diff | chatcli -p "Summarize" |
Shared backend with TLS 1.3, JWT/RBAC, failover, Prometheus metrics, MCP, and plugin discovery. chatcli server --port 50051 \
--token my-token
chatcli connect \
--server host:50051 \
--token my-token |
Autonomous AIOps pipeline with 17 CRDs, 54+ remediation actions, SLO monitoring, and post-mortems. helm install chatcli-operator \
oci://ghcr.io/diillson/charts/chatcli-operator \
--namespace chatcli-system \
--create-namespace |
The scheduler runs embedded in the CLI and optionally as a daemon. Jobs survive restarts via WAL + snapshot.
# Fire a command in 30s
/schedule ping --when +30s --do "/run curl https://api.example.com/health"
# Daily cron with retry
/schedule backup --cron "0 2 * * *" --do "shell: ./backup.sh" --max-retries 3
# Deploy + K8s wait + trigger smoke
/schedule deploy --when +0s --do "shell: terraform apply -auto-approve" \
--wait "k8s:deployment/prod/api:Available" --timeout 15m \
--triggers smoke-tests
# Daemon to keep running with the CLI closed
chatcli daemon start --detach
chatcli daemon status
# List / inspect / cancel
/jobs list
/jobs show <id>
/jobs tree
/jobs cancel <id>Agents get the @scheduler tool and can pause themselves waiting on conditions — see Cookbook: scheduler automation and the feature doc.
Context commands (CLI mode)
Inject environment data directly into your prompt:
| Command | Description |
|---|---|
@git |
Status, branches, and recent commits |
@file <path> |
File or directory contents |
@env |
Environment variables |
@history |
Recent shell commands |
@command <cmd> |
Execute a command and inject its output |
Kubernetes manifest example (Instance CRD)
apiVersion: platform.chatcli.io/v1alpha1
kind: Instance
metadata:
name: chatcli-prod
spec:
provider: ZAI
model: glm-5
replicas: 2
fallback:
enabled: true
providers:
- name: OPENAI
model: gpt-5.4
- name: MINIMAX
model: MiniMax-M2.7helm install chatcli oci://ghcr.io/diillson/charts/chatcli \
--namespace chatcli --create-namespace \
--set llm.provider=OPENAI --set secrets.openaiApiKey=sk-xxx15 providers with a unified interface. Automatic failover with intelligent error classification, cross-provider extended thinking, and prompt caching where available.
| Provider | Default Model | Tool Calling | Vision | Reasoning / Thinking |
|---|---|---|---|---|
| OpenAI | gpt-5.4 | Native | Yes | reasoning_effort (o-series / gpt-5) |
| Anthropic (Claude) | claude-sonnet-4-6 | Native | Yes | Extended thinking with cache |
| AWS Bedrock | claude-sonnet-4-5 | Native | Yes | Thinking budget (Anthropic models) |
| Google Gemini | gemini-2.5-flash | Native | Yes | — |
| xAI (Grok) | grok-4.3 | XML fallback | — | — |
| ZAI (Zhipu AI) | glm-5 | Native | Yes | ZAI_THINKING=enabled|disabled · GLM Coding Plan via ZAI_USE_CODING_PLAN |
| MiniMax | MiniMax-M2.7 | Native | Yes | — |
| Moonshot (Kimi) | kimi-k2.6 | Native | Yes | MOONSHOT_THINKING=enabled|disabled|auto |
| GitHub Copilot | gpt-4o | Native | Yes | — |
| GitHub Models | gpt-4o | Native | Yes | — |
| StackSpot AI | StackSpotAI | — | — | — |
| OpenRouter | openai/gpt-5.2 | Native | Yes | Passthrough |
| Ollama | (local) | XML fallback | — | <thinking> tag normalization |
| Devin CLI (Cognition) | claude-sonnet-4.6 | XML fallback | — | Model-dependent (server-side) |
| OpenAI (Responses API) | gpt-5.4 | Native | Yes | reasoning_effort |
# Configurable fallback chain
CHATCLI_FALLBACK_PROVIDERS=OPENAI,CLAUDEAI,BEDROCK,ZAI,MINIMAX,MOONSHOT,OPENROUTER/thinking on|off|auto enables extended thinking / reasoning_effort on any provider that supports it — the cross-provider mapping is automatic.
ReAct engine (Reason + Act) with 14 built-in agents: 12 orchestration specialists running in parallel (
file, coder, shell, git, search, planner, reviewer, tester, refactor, diagnostics, formatter, deps) + 2 quality-harness agents (refiner,verifier).
/coder "Refactor the auth module to use JWT"
chatcli -p "Create tests for the utils package" --agent-auto-exec| Agent | Responsibility |
|---|---|
| File | File reading, writing, and manipulation |
| Coder | Code generation and editing |
| Shell | System command execution |
| Git | Version control operations |
| Search | Code and file search |
| Planner | Complex task decomposition (Plan-and-Solve / ReWOO) |
| Reviewer | Automated code review |
| Tester | Test generation and execution |
| Refactor | Safe code refactoring |
| Diagnostics | Problem analysis and debugging |
| Formatter | Formatting and linting |
| Deps | Dependency management |
| Refiner | Self-Refine post-hook (critique → revise) |
| Verifier | Chain-of-Verification (questions + final answer) |
Workers are coordinated by the dispatcher with a configurable semaphore (CHATCLI_AGENT_MAX_WORKERS), retry policy, and FileLockManager synchronization.
Seven prompting/execution patterns composed via a pluggable pipeline with state machine, hot reload, and per-hook isolation.
| # | Pattern | Status | Opt-in |
|---|---|---|---|
| 1 | ReAct (Reason + Act) | ✅ agent core | — |
| 2 | Plan-and-Solve / ReWOO | ✅ | /plan, CHATCLI_QUALITY_PLAN_FIRST_MODE |
| 3 | Reflexion (with durable queue) | ✅ | on by default |
| 4 | RAG + HyDE | ✅ | CHATCLI_QUALITY_HYDE_ENABLED=1 |
| 5 | Self-Refine (with semantic convergence) | ✅ | CHATCLI_QUALITY_REFINE_ENABLED=1 |
| 6 | Chain-of-Verification (CoVe) | ✅ | CHATCLI_QUALITY_VERIFY_ENABLED=1 |
| 7 | Cross-provider reasoning backbone | ✅ | CHATCLI_QUALITY_REASONING_MODE=auto |
- State machine (Active → Draining → Closed) with atomic CAS transitions.
- Copy-on-Write via
atomic.Pointer[snapshot]—AddPre/AddPost/SwapConfigare atomic, zero locks on the hot path. - Per-hook isolation: panic recovery, timeout enforcement (default 30s), circuit breaker (5 failures → open for 30s).
- Priority-based ordering via optional
Prioritizedinterface (backward-compatible — unmarked hooks default to 100). - Short-circuit sentinels:
ErrSkipExecution(cache-hit beforeagent.Execute) andErrSkipRemainingHooks(ensemble patterns). - Graceful shutdown via
DrainAndClose(timeout)honoring in-flight calls.
Reflexion triggers (error, hallucination flagged by CoVe, low quality) flow through a lesson queue with enterprise guarantees — lessons survive process crashes:
- WAL with double CRC32, atomic rename, dir fsync — torn writes detected automatically.
- Worker pool (default 2) with per-job timeout, exponential backoff with jitter, configurable
MaxAttempts. - Persistent DLQ (same WAL format) with
/reflect failed,/reflect retry <id>,/reflect purge <id>. - Drain-on-boot: pending lessons from a previous session are reprocessed automatically.
- Idempotency via
sha256(task | trigger | attempt)— re-triggering the same situation is a no-op. - Stale discard (default 7d) — old lessons dropped at replay time.
/reflect list # current queue + DLQ
/reflect failed # DLQ with last error per entry
/reflect retry <job-id> # re-queue a failed lesson
/reflect purge <job-id> # permanently remove a DLQ entry
/reflect drain # force WAL replaySelf-Refine uses a char → Jaccard → embedding cascade to detect when to stop iterating. Catches "same meaning, different words" that the char-level heuristic missed:
| Stage | Cost | When it fires |
|---|---|---|
| Char | μs | Always. Early-exit when sim > 0.99 (identical) or sim < 0.3 (diverged) |
| Jaccard | ms | Borderline, normalized token sets with EN/PT stop-words |
| Embedding | ms + $ | Borderline after Jaccard. Opt-in via CHATCLI_QUALITY_REFINE_CONVERGENCE_EMBEDDING=1 |
- LRU cache with TTL (default 256 entries / 5min) avoids re-embedding identical text.
- Per-scorer circuit breaker — provider outage degrades to Jaccard without blocking refine.
- Quality regression detection: when pass N gets worse (>15% sim loss vs best) → revert to best draft + set
refine_rolled_backmetadata so Reflexion can learn. - Strict mode: refuses to declare convergence without embedding when stakes are high.
Full quality pipeline config
# Master switch
CHATCLI_QUALITY_ENABLED=true
# Self-Refine (#5) + semantic convergence
CHATCLI_QUALITY_REFINE_ENABLED=false # opt-in
CHATCLI_QUALITY_REFINE_MAX_PASSES=1
CHATCLI_QUALITY_REFINE_CONVERGENCE_ENABLED=true
CHATCLI_QUALITY_REFINE_CONVERGENCE_EMBEDDING=false
CHATCLI_QUALITY_REFINE_CONVERGENCE_STRICT=false
# Chain-of-Verification (#6)
CHATCLI_QUALITY_VERIFY_ENABLED=false
CHATCLI_QUALITY_VERIFY_NUM_QUESTIONS=3
CHATCLI_QUALITY_VERIFY_REWRITE=true
# Reflexion (#3) + durable queue
CHATCLI_QUALITY_REFLEXION_ENABLED=true
CHATCLI_QUALITY_REFLEXION_QUEUE_ENABLED=true # WAL + worker pool + DLQ
CHATCLI_QUALITY_REFLEXION_QUEUE_WORKERS=2
CHATCLI_QUALITY_REFLEXION_QUEUE_MAX_ATTEMPTS=5
CHATCLI_QUALITY_REFLEXION_QUEUE_STALE_AFTER=168h
# Plan-and-Solve / ReWOO (#2)
CHATCLI_QUALITY_PLAN_FIRST_MODE=auto # off|auto|always
# HyDE (#4)
CHATCLI_QUALITY_HYDE_ENABLED=false
CHATCLI_QUALITY_HYDE_USE_VECTORS=false
# Reasoning backbone (#7)
CHATCLI_QUALITY_REASONING_MODE=auto # off|on|auto
CHATCLI_QUALITY_REASONING_BUDGET=8000All exposed via /config quality with runtime state (registered hooks, queue depth, DLQ size).
End-to-end Prometheus integration in the
chatclinamespace. 50+ metrics covering LLM, agents, pipeline, queue, and lesson queue.
chatcli server --port 50051 --metrics-port 9090
curl http://localhost:9090/metrics | grep chatcli_
curl http://localhost:9090/healthz| Subsystem | Metric | Type |
|---|---|---|
chatcli_llm_* |
requests_total, request_duration_seconds, tokens_used_total, errors_total |
Counter, Histogram |
chatcli_quality_pipeline_* |
dispatch_total, hook_duration_seconds, hook_errors_total, hook_circuit_state, generation |
Counter, Histogram, Gauge |
chatcli_lessonq_* |
enqueue_total, queue_depth, dlq_size, processing_duration_seconds, wal_corruption_total, retry_total |
Counter, Gauge, Histogram |
chatcli_session_* |
duration, commands executed, signals | Counter, Gauge |
chatcli_grpc_* |
unary + stream interceptors | Counter, Histogram |
Standard Go runtime and process_* collectors are registered automatically.
Security is not a feature flag. It is the foundation of every layer of ChatCLI.
|
Authentication & authorization
Encryption
Network
|
Plugin & agent security
Auditing & compliance
CI/CD security
|
Built-in OAuth
/auth login openai-codex # OAuth PKCE + local callback
/auth login anthropic # OAuth PKCE + manual code
/auth login github-copilot # Device Flow (RFC 8628)
/auth status # All provider status
Credentials are stored with AES-256-GCM at ~/.chatcli/auth-profiles.json.
| Category | Commands |
|---|---|
| Core | /help · /version · /update [check] · /reload · /exit · /reset |
| Sessions | /session {save,load,attach,detach,status,list,delete,new,fork,search} · /export · /newsession · /rewind |
| Context | /context {create,attach,list,remove} · @git · @file · @env · @history · @command |
| Config | /config [section] · /status · /settings · /switch <provider|model> |
| Agent mode | /agent [task] · /run · /coder · /plan [query] · /moa <prompt> |
| Quality pipeline | /thinking [on|off|auto] · /refine [draft] · /verify [answer] · /reflect [list|failed|retry|purge|drain|<text>] |
| Memory & graph | /memory {longterm,list,profile,facts,remember,forget,profile set,compact} · @memory (remember/recall/forget/profile/neighbors/map) — profile with lifecycle: list fields upsert (restating an item supersedes instead of duplicating) and _replace/_done/_remove key suffixes rewrite (e.g. goals_done= removes the finished goal; record milestone= and certifications= alongside); new interests, directives (hard rules vs preferences; per-project scope with "[scope:<project>] rule" — injected only when the matching workspace is active), milestone (dated timeline), stance (technical position with its why, "position :: reason") and env_<key> (structured environment) fields; per-field provenance+freshness (user vs extraction, re-affirmation bumps confirmed_at, aging fields get flagged as possibly stale) and a privacy tier (finance/health/family keys auto-tagged [sensitive]: they personalize answers but never enter code/examples/artifacts; sensitive_mark/sensitive_unmark); daily notes consolidate into weekly and monthly digests (Trajectory section in context); profile updates also work in chat (sanctioned exception, /config chat memory, CHATCLI_CHAT_MEMORY) · /graph [subject] · /compact [ratio] |
| Extensibility | /mcp {init,list,invoke,config} · /plugin {list,load,unload} · /skill <name> · /hooks {list,enable,disable,test} |
| Messaging & Servers | /gateway {start,status} (Telegram/Slack/Discord/WhatsApp/webhook) · chatcli mcp-server · chatcli acp |
| Remote | /auth {login,logout,status} · /connect <server> · /disconnect |
| Tools | /watch {pid|file} · /worktree {create,list,remove} · /channel {create,switch} · /websearch <query> · /lsp <file> — plus agent builtins @browser, @forge, @view, @proc (background + interactive PTY), @taskgraph (verified DAG orchestration, watch with /taskgraph), and @coder subcommands outline/map/checkpoint |
| Scheduler | /schedule <name> --when <t> --do <a> · /wait --until <cond> · /jobs {list,show,tree,cancel,pause,resume,logs,daemon} · chatcli daemon {start,stop,status,ping,install} |
| Diagnostics | /metrics · /cost · /ratelimit (/limits) |
Every feature is designed to compose with the others. Plugins discover skills. Hooks drive tools. Contexts feed agents.
| Feature | Description |
|---|---|
| Native tool calling | Native APIs from OpenAI, Anthropic, Bedrock, Google, ZAI, MiniMax, Moonshot, OpenRouter. ephemeral cache for Anthropic. Automatic XML fallback for providers without native support. |
| Browser automation (@browser) | Drives a real local Chrome/Chromium/Brave/Edge over the DevTools Protocol — spoken straight over the shipped websocket client, no new dependency, no driver, no key. open/snapshot (page as text with numbered interactive elements)/click/type/eval/screenshot/console/network. The verification loop for web work: build a frontend, then SEE it and debug it from its console/network. CHATCLI_BROWSER_BIN, CHATCLI_BROWSER_HEADLESS. |
| Git forge (@forge) | Pull requests, issues and CI through the user's OWN authenticated gh/glab — keyless, auto-detected from the git remote. pr-list/view/diff/checks/create/comment, issue-*, ci-status, ci-logs (failed-step logs). Closes the loop branch → PR → watch CI → fix without leaving the agent; reads auto-approved, mutations behind the security gate. |
| Image input (@view) | The agent LOOKS at a local image mid-task — a @browser screenshot, a mock, a diagram — through the vision pipeline (native multimodal or describe-fallback), staged and attached on the next turn. |
| Task graph (@taskgraph) | An approved multi-task plan becomes a persisted DAG: independent tasks run in parallel on squad workers, dependencies gate execution, and done is never the executor's self-report — the engine runs each task's validation commands itself and a fresh reviewer worker issues the verdict (done or retry with feedback). Real per-task cost from provider usage, shadow-git checkpoint before each executor, resumable runs under ~/.chatcli/taskgraph/. Humans watch mid-run via /taskgraph (status, per-task evidence, cancel) or the live browser dashboard (/taskgraph dash): animated DAG canvas with phase swimlanes, pan/zoom, per-task popovers with reviewer evidence and gate outputs, critical path and real per-task cost — served read-only on 127.0.0.1, so closing it never affects the run. Worth it from ~5+ genuinely independent tasks. |
| Exec sandbox | Opt-in OS-level confinement for @coder exec: CHATCLI_CODER_SANDBOX=off|workspace|strict|docker. Native sandbox-exec (macOS) / bwrap (Linux) / Docker-Podman container on ANY OS incl. Windows; strict also cuts the network. Confines what a permitted command can touch, on top of the validator and policy that gate what runs. |
| Shadow-git checkpoints | An automatic workspace snapshot before every mutating @coder subcommand, into a shadow git repo under ~/.chatcli — your own .git is never touched. @coder checkpoint {list,create,restore} rewinds multi-file edits and exec side effects. Snapshots are bounded: workspaces as broad as your home directory are never auto-snapshotted, each snapshot runs under a hard deadline (CHATCLI_CODER_CHECKPOINT_TIMEOUT seconds), and repeated failures back off and disable snapshots for the session. CHATCLI_CODER_CHECKPOINTS=off. |
| Post-edit diagnostics | After a successful @coder write/patch, the language server's diagnostics for the touched files are auto-injected into the tool result — a broken edit is caught turns earlier than a failing test. CHATCLI_CODER_AUTODIAG=off. Plus @coder outline/map for code-structure orientation (repo map via go/ast) without reading whole files. |
| Interactive processes (@proc pty) | @proc start {pty:true} runs a program on a real pseudo-terminal (REPLs, debuggers, ssh) and @proc stdin types into it — programs that demand a TTY no longer dead-end the agent (Unix-first). |
| MCP (Model Context Protocol) | Client via stdio, SSE, and streamable HTTP for expanded context. Remote (HTTP/SSE) servers gated behind OAuth 2.1 are supported end-to-end: on a 401 the client discovers the authorization server (RFC 9728/8414), registers dynamically (RFC 7591), runs a PKCE browser flow, and refreshes tokens transparently (stored AES-256-GCM in the encrypted auth store). Authorize with /mcp login <server>, or let the agent call the @mcp-login tool when a call reports "authorization required". Server (chatcli mcp-server) exposes the FULL surface: every built-in tool with read-only annotations, the agent/coder loops with per-call provider/model routing and quality-harness toggles, provider discovery, and all installed skills served as MCP prompts — plus every tool discovered from the MCP servers ChatCLI itself is connected to, re-exported under their mcp_* names with the origin JSON Schema intact (ChatCLI as an MCP hub: many servers aggregated behind one endpoint, with tools/list_changed notifications as they connect). Exposure policy via CHATCLI_MCP_TOOLS (all/safe/allowlist; safe honors the origin readOnlyHint, allowlists name proxied tools as mcp_<tool>). Clients also get manage_session (save/load/attach/detach/status/list/delete/clear/search/fork the conversations behind ask_chatcli's session parameter, sharing the /session store; save/load/attach bind the live session so every turn is written through and writes from other surfaces — REPL, gateway, another server — are adopted before each turn: cross-surface session continuity) and list_providers with live API model listings merged with the catalog — the same discovery the interactive picker uses. Full-experience parity: ask_chatcli runs the SAME pipeline as an interactive turn — the user's long-term memory and profile, /context attachments per session, pinned and trigger-activated skills, knowledge retrieval and token-aware compaction (plain=true keeps a raw passthrough) — and agent_task runs the real ReAct loop with session-scoped contexts. Local state is browsable as MCP resources under chatcli:// URIs (memory index/longterm/profile/projects, contexts, knowledge TOC + paged documents, skills with triggers, saved sessions; CHATCLI_MCP_RESOURCES=off disables). The server joins the conversation hub in resume mode, so a thread started in the REPL or on a gateway channel continues from any MCP client (CHATCLI_MCP_HUB=off opts out, CHATCLI_MCP_HUB_PRINCIPAL isolates). Dangerous commands auto-approve like the gateway daemon; set CHATCLI_MCP_DANGER=block to decline them in-band instead. ACP server (chatcli acp) with chat/agent/coder session modes, live streaming, cancellation and session/load restore (capability loadSession: true — a prior session id comes back from live state or its autosave mirror, with the conversation replayed to the client; /session from the prompt box operates per session and joins the same cross-surface continuity), for editors (Zed) and agent-to-agent use. |
| Chat Gateway | Runs as a messaging daemon (Telegram, Slack, Discord, WhatsApp, webhook): each message runs through the agent loop and progress is streamed back to the chat. Voice messages are transcribed (local-first whisper) and answered in voice by default (CHATCLI_GATEWAY_VOICE_REPLY=auto|always|never); each conversation controls it by asking in natural language ("answer me in audio" / "stop sending audio") via the @voice tool, with the preference persisted. |
| Embedded voice (TTS) | CHATCLI_TTS_PROVIDER=embedded — offline Kokoro neural voice, no API key and no cgo: downloads the sherpa-onnx engine + model once (~150MB) and works the same on Linux/macOS/Windows. Routes pt-BR/English by reply language (CHATCLI_TTS_VOICE=bm_george, CHATCLI_TTS_VOICE_PT=pm_alex); the other backends (say/espeak, self-hosted, OpenAI/Groq/Gemini) remain available. |
| Embedded transcription (STT) | Offline multilingual Whisper via sherpa-onnx, no API key and no cgo — and the automatic fallback: with nothing configured, the gateway downloads the engine + an ONNX model once (~200MB for base; CHATCLI_TRANSCRIPTION_MODEL=tiny|base|small|…) at startup and transcribes voice notes auto-detecting the spoken language. OGG/Opus voice notes (Telegram/WhatsApp) decode in pure Go — no ffmpeg needed; only residual formats (mp3/m4a) require ffmpeg, and the gateway preflight + /gateway status warn with your platform's install command. CHATCLI_TRANSCRIPTION_PROVIDER=embedded forces it over the other backends (local whisper CLI, self-hosted, Groq/OpenAI), which remain available. |
| Mixture-of-Agents | /moa — several models propose in parallel and an aggregator synthesizes (Wang et al., 2406.04692). Every participant gets the same briefing as a chat turn (attached contexts, workspace memory, skills) plus read-only knowledge retrieval, CCR recall and long-term memory recall. |
| Model routing (@model) | The agent routes itself: @model list shows every provider's models with a price-derived tier (fast-cheap/balanced/frontier), cost per 1M tokens, context window and capabilities; use switches the rest of the task to another model/provider (task-scoped, never mutates the session); delegate one-shots a subtask on a cheaper model keeping the main loop's history and prompt cache intact. Kill switch: CHATCLI_AGENT_MODEL_TOOL=false. |
| LSP diagnostics | /lsp <file> — compiler errors/warnings via the Language Server Protocol (gopls, pyright, rust-analyzer, clangd, …). |
| Rate limits | /ratelimit — provider limits parsed from x-ratelimit-* headers (requests/tokens, % used, reset). |
| Trajectory export | /export — current conversation as ShareGPT JSONL for fine-tuning/analysis. |
| Persistent contexts | /context create, /context attach — inject whole projects into the system prompt with cache hints. |
| Knowledge base (keyless RAG) | /context create docs corpus.jsonl --mode knowledge — documentation corpora (e.g. JSONL from the builtin @docs-flatten tool, which flattens local or git-repo Markdown/MDX docs) become a knowledge base: attaching injects only an index card (~900 fixed tokens, even at 6MB+) and relevant passages are retrieved per turn via pure-Go BM25 (no API key) + embeddings when configured. The @knowledge tool (search/get/toc) interrogates the base iteratively in agent/coder and also in chat (read-only exception, /config chat knowledge) — including authoring skills from the docs with @skill. |
| Bootstrap & Memory | SOUL.md, USER.md, IDENTITY.md, RULES.md + long-term memory with facts (confidence + provenance + contradiction reconciliation), topics with rolling summaries, and decay. |
| Self-evolution | Skills author and evolve themselves on the memory extraction pass (no extra LLM call): reusable procedures become auto-activating skills; an insight evolves an existing skill by additive merge, with a reversible backup (@skill restore). CHATCLI_SELFEVOLVE_MODE=off|suggest|auto; observability under /config selfevolve. |
| Knowledge graph (Obsidian in the core) | Facts, topics, projects, skills and tags become an on-demand graph: @memory neighbors <subject> / map pull backlinks and related notes, a tiny index card rides each turn, and /graph [subject] renders the graph to an image (embedded go-graphviz). CHATCLI_GRAPH_INDEX=on|off. |
| Plugins | Auto-detection, schema validation, Ed25519 signatures, remote plugins. |
| Skills | Self-authoring (@skill), multi-registry (skills.sh, ClawHub, ChatCLI.dev), fuzzy search, security audits, source preferences, atomic install. |
| Slash commands | Markdown prompt templates invoked as /name args on EVERY surface (REPL, coder mid-run, one-shot, gateway, ACP, MCP prompts) and with every provider — expansion is pure prompt rewriting. Project .chatcli/commands/ + personal ~/.chatcli/commands/, with zero-migration interop for Claude Code, Devin, Windsurf, Cursor, opencode, Codex, Gemini CLI, Qwen Code and GitHub Copilot command files (their placeholder and TOML dialects included). ! pre-execution runs through the coder security gate; allowed-tools scopes the run; the model discovers the catalog via @commands. A command that needs tools declares mode: coder (inferred automatically when allowed-tools is present) and, invoked from chat, is auto-routed through a coder one-shot run — it executes and returns to chat instead of being refused by the tool-less chat mode (mode: chat vetoes the inference; opt out globally with CHATCLI_COMMANDS_AUTOROUTE=off). Panel under /config commands. |
| Custom personas | Markdown with YAML frontmatter (model, tools, skills). |
| Hooks | PreToolUse, PostToolUse, SessionStart/End, UserPromptSubmit, Pre/PostCompact — shell or webhook. |
| WebFetch / WebSearch | DuckDuckGo + fetch with text extraction. |
| Cost tracking | Real API usage across all providers, /cost (+ reset, last, sessions, export), session budgets with optional hard stop, persisted snapshots. |
| Git Worktrees | Isolated work on parallel branches. |
| K8s Watcher | Multi-target: metrics, logs, events, Prometheus scraping. |
| i18n | Portuguese and English with automatic detection. |
| Session management | Save, load, fork, export. |
chatcli/
cli/
agent/
quality/ 7-pattern pipeline (state machine + COW snapshots)
convergence/ Semantic convergence (char → jaccard → embedding)
lessonq/ Reflexion durable queue (WAL + worker pool + DLQ)
workers/ 14 agents + dispatcher + FileLockManager
hooks/ Lifecycle events (shell/webhook)
mcp/ MCP client (stdio, SSE, HTTP + OAuth)
plugins/ Plugin manager + signature verification
scheduler/ Chronos — durable scheduler (WAL + cron + DAG + daemon)
condition/ 10 evaluators (shell, http, k8s, docker, tcp, llm, ...)
action/ 8 executors (slash, shell, agent, webhook, ...)
builtins/ Aggregated registry for evaluators + executors
workspace/memory/ Facts, topics, patterns, vector index (HyDE)
tui/ Bubble Tea adapters
llm/
openai/ openai_responses/ openai_assistant/
claudeai/ bedrock/
googleai/ xai/ zai/ minimax/
copilot/ github_models/ stackspotai/ openrouter/ ollama/
fallback/ catalog/ registry/ token/ toolshim/ embedding/
metrics/ Prometheus registry + /metrics + /healthz
server/ gRPC + TLS + JWT + MCP + plugin discovery
operator/ Kubernetes Operator (17 CRDs, AIOps pipeline)
k8s/ Watcher (collectors, store, summarizer)
models/ ToolDefinition, ToolCall, LLMResponse, Message
auth/ OAuth PKCE, Device Flow, AES-256-GCM store
config/ ConfigManager with versioned migration
i18n/ embed.FS + golang.org/x/text (PT / EN)
Design principle: each package declares its own interfaces and self-registers. The
llm/registry lets you add a new provider by implementing a single interface. The quality pipeline is pluggable viaAddPre/AddPostwith atomic swap. The operator coordinates independent CRDs via the controller pattern.
- CI (
.github/workflows/1-ci.yml): golangci-lint, gofmt,go vet,go test -race -coverprofile, coverage HTML as artifact. - Security scan (
security-scan.yml): continuous Trivy image scanning. - Release automation (
release-please+publish-release.yml): multi-platform builds, cosign signatures, CycloneDX SBOM, ArtifactHub publishing. - Makefile:
make build,make test,make lint,make installwithVersion,CommitHash,BuildDateinjected via ldflags.
- Fork the repository
- Create a branch from
main:git checkout -b feature/my-feature - Commit and push
- Open a Pull Request
See docs/ for detailed architecture, quality pipeline, and operator guides.
Documentation • Releases • Helm Charts • Go Reference • Issues
