Local-first dashboard for Claude Code cost, token, tool-usage, and full-text search analytics
Project description
Argus
Local-first analytics + persistent archive for Claude Code. Argus reads
your ~/.claude/ session logs, computes cost from a bundled pricing table,
and serves a dashboard at http://localhost:4242 that tells you exactly how,
when, and how much you've been using Claude Code.
Claude Code rotates its own session files (cleanupPeriodDays defaults to
30). Once Argus ingests a session into ~/.argus/argus.db, the row stays
forever — so a few months in, Argus knows about sessions Claude has already
deleted. Live tools like ccusage can only show what's currently on disk;
Argus accumulates.
Everything stays on your machine. No telemetry, no API calls, no embeddings — just SQLite and a static web UI.
pipx install argus-code # or: uv tool install argus-code
argus start
That's it. Your default browser opens to the dashboard once the first-pass ingest finishes (~5–10s for a typical install).
What it shows you
| Page | What it answers |
|---|---|
| Overview | How many tokens have I burned? How much would I have paid on the API? Where does my spend land each day? Plus a "What needs attention" card that surfaces detector findings (e.g. a tool whose error rate spiked this week). |
| Sessions | Sortable table of every session — project, model, tokens, cost, duration. Click any row to drill in. |
| Tools | Tool-call leaderboard (Bash vs Edit vs Read vs WebFetch…), error rates per tool, MCP server breakdown, sub-agent invocations. |
| Search (opt-in) | Full-text search over every prompt you've typed AND every assistant response, your replies, and tool output. SQLite FTS5, sub-millisecond, no embeddings. |
| Trends | Tokens and cost bucketed by day / week / month, grouped by model. |
| Models | Per-model token mix and cost rollup. |
| Settings | Search-indexing toggle, pricing version, parse errors, data export. |
CLI
argus # top-level command group
├─ start [--port 4242] [--host 127.0.0.1] [--data-dir <path>]
│ # watcher + ingester + dashboard server
├─ pricing
│ └─ refresh # pull latest model prices from LiteLLM
├─ search
│ ├─ status # is transcript indexing on?
│ ├─ enable # turn it on (next start backfills)
│ ├─ disable # turn it off, keep data
│ └─ clear # wipe all indexed segments + disable
├─ claude # scaffold & manage .claude/ setups
│ ├─ init [path] [--template <name>] [--force]
│ │ # stamp CLAUDE.md + .claude/ into a project
│ └─ template
│ ├─ list # list templates (bundled + user)
│ └─ create <name> [--path <dir>] [--all]
│ # save a project's .claude/ as a template
└─ wipe # delete ~/.argus/ entirely
Run --help at any level for details — argus --help, argus claude --help,
argus claude template --help.
argus claude — project scaffolding
Set good agent config before you run, not just observe it after. init
copies a template into a project: CLAUDE.md goes to the project root,
everything else into .claude/. Existing files are skipped (use --force
to overwrite) — but an existing CLAUDE.md is never overwritten, even
with --force. The bundled default template ships a sensible
settings.json, agents, commands, rules, and a placeholder skill. Save your
own project's setup as a reusable template with template create; user
templates live in ~/.argus/templates/ and take precedence over bundled ones.
Privacy & security
Argus is built for one user on one machine. The defaults reflect that:
- Server binds to
127.0.0.1only. Nothing on your LAN/Wi-Fi/VPN can reach the dashboard. Useargus start --host 0.0.0.0if you really want LAN exposure — it prints a loud warning when you do. - No external requests, ever, except
argus pricing refreshwhich is a manual command that fetches one JSON file from LiteLLM's GitHub. No telemetry, no analytics pings, no LLM calls. - Transcript indexing is opt-in. Cost-and-token analytics work out of
the box without indexing any text content. Full-text search across
prompts and transcripts requires explicit opt-in via Settings or
argus search enable. Opting out actually means out — the API returns empty results, even if data is on disk. - Cross-origin POSTs are rejected. The state-changing endpoints
(
/api/search-index/*) check theOriginheader so a random tab in your browser can't silently wipe your data while argus is running. - No embeddings, no model weights. Search uses SQLite FTS5 — pure inverted-index lexical search. Lookups are deterministic and offline.
Data lives at ~/.argus/argus.db. Delete it any time with argus wipe
(or just remove the file).
For vulnerability reports, see SECURITY.md.
How it works
- Ingest. A
watchdogobserver tails every~/.claude/projects/<project>/<session-id>.jsonlfile. Lines are validated withpydantic, deduplicated bymessage.id, and turned into normalized session/turn rows in SQLite (WAL mode). - Cost. Per-turn cost comes from a bundled
pricing/<version>.jsontable sourced from LiteLLM. Tokens are exact; costs are estimates and the dashboard says so. - Tools. Each
tool_useblock in the JSONL becomes a row intool_calls. Errors come from matchingtool_result.is_errorin the next user message. MCP servers are extracted from tool names matchingmcp__<server>__<tool>. - Search (opt-in). Two FTS5 virtual tables: one over
~/.claude/history.jsonl(every prompt you've ever typed, ~150 KB indexed for a heavy user), one over assistant text + thinking blocks + user content + tool output (~30–60 MB for hundreds of sessions). Indexing happens incrementally during the normal ingest tick. - Dashboard. Astro 5 + ECharts, statically built, served by the FastAPI app (uvicorn). No server-side rendering, no Node code in the browser.
- Detection (alerts). A lightweight scheduler thread runs registered
detectors on a fixed cadence. Each detector reads the DB and returns
findings; the scheduler is the sole writer, upserting them into an
alertstable — idempotent, with aresolved_atlifecycle so an issue that recovers then recurs fires again instead of staying silent. The Overview's "What needs attention" card reads these, and critical findings raise a browser notification. The v1 detector flags tools whose error rate spiked versus their preceding 4-week baseline.
Configuration
| Where | Knob |
|---|---|
argus start --port <n> |
Pick a different port (default 4242). |
argus start --host <h> |
Bind host (default 127.0.0.1). Pass 0.0.0.0 for LAN exposure. |
argus start --data-dir <path> |
Override ~/.argus/. |
pricing/*.json |
Bundled price tables. Refresh with argus pricing refresh. |
Requirements
- Python ≥ 3.11. Argus uses the stdlib
sqlite3module — make sure your Python was built with FTS5 (the standard CPython distributions for macOS, Linux, and Windows all are). Argus checks at startup and fails with a clear error if FTS5 is missing. - A
~/.claude/directory containing real session JSONL — i.e. you've used Claude Code at least once. Argus exits with a friendly message if it's missing.
Keep your history longer
By default Claude Code deletes session files after 30 days. To extend the
window, set cleanupPeriodDays in ~/.claude/settings.json:
{
"cleanupPeriodDays": 365
}
The minimum is 1; there's no way to disable cleanup entirely. Whatever you set, Argus's own database keeps the data even after Claude rotates it out.
Development
git clone https://github.com/KrishBhimani/argus-code.git
cd argus-code
uv sync # install deps + create venv
uv run pytest # ~215 tests, ~20s
uv run argus start # dev — runs directly from source
The dashboard is an Astro project under dashboard/ and still builds via
npm at release time only. End users never touch npm.
Source layout:
python/argus/ Python ingest, store, server, CLI
adapters/ Claude Code JSONL parsers + adapter registry
store/ SQLite schema + migrations + repo
server/ FastAPI app + /api routes
collector/ watcher + pipeline + first-run + search backfill + alert scheduler
detectors/ alert detectors (pure reads) + @register registry
scaffold/ `argus claude` template storage / init / snapshot
pricing/ LiteLLM-derived price table + cost compute
schema/ pydantic data models
dashboard/ Astro source
dashboard-dist/ Astro build output (shipped in wheel as data)
pricing/ Bundled pricing JSON (shipped in wheel as data)
templates/ Bundled .claude/ scaffolding templates (shipped in wheel as data)
tests/ pytest suite, mirrors python/argus/ layout
License
MIT — see LICENSE.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file argus_code-0.2.0.tar.gz.
File metadata
- Download URL: argus_code-0.2.0.tar.gz
- Upload date:
- Size: 457.7 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.6.10
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0ffb50d175149e0c1de62a3df7ada9220d0332e4e895da754855a076f222a0be
|
|
| MD5 |
e0c35d977ba6df30c9fe7017d957b9fe
|
|
| BLAKE2b-256 |
5b60b87e859628175ace68464c24caef92f034c75ca5e4f65a6cfe4ba2497501
|
File details
Details for the file argus_code-0.2.0-py3-none-any.whl.
File metadata
- Download URL: argus_code-0.2.0-py3-none-any.whl
- Upload date:
- Size: 315.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.6.10
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
6868c7eda6c1480aab198d03737129bb9581d19a54aea0395c52150daa9f5e94
|
|
| MD5 |
25bf967acc10b9d013171aadc6ef0083
|
|
| BLAKE2b-256 |
1397036cb5208c97462c12322f5eca16c71ca21cf044a2262646452fb045bfbb
|