Metadata-Version: 2.4
Name: tce-monitor
Version: 0.2.0
Summary: Terminus Cancrorum Est — monitor Claude Code processes, token usage, and costs
Project-URL: Homepage, https://github.com/tmancino/Terminus-Cancrorum-Est
Project-URL: Repository, https://github.com/tmancino/Terminus-Cancrorum-Est
Project-URL: Issues, https://github.com/tmancino/Terminus-Cancrorum-Est/issues
Author-email: Tommy Mancino <tom.mancino@gmail.com>
License-Expression: MIT
License-File: LICENSE
Keywords: claude,claude-code,monitor,process-monitor,token-usage
Classifier: Development Status :: 4 - Beta
Classifier: Environment :: Console
Classifier: Environment :: MacOS X
Classifier: Environment :: Web Environment
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Operating System :: MacOS
Classifier: Operating System :: POSIX :: Linux
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Topic :: Software Development :: Quality Assurance
Classifier: Topic :: System :: Monitoring
Classifier: Topic :: Utilities
Requires-Python: >=3.11
Requires-Dist: fastapi>=0.115.0
Requires-Dist: jinja2>=3.1.0
Requires-Dist: psutil>=5.9.0
Requires-Dist: pydantic-settings>=2.0.0
Requires-Dist: pydantic>=2.0.0
Requires-Dist: python-dotenv>=1.0.0
Requires-Dist: uvicorn>=0.30.0
Provides-Extra: dev
Requires-Dist: httpx>=0.27; extra == 'dev'
Requires-Dist: mypy>=1.10; extra == 'dev'
Requires-Dist: pytest-asyncio>=0.23; extra == 'dev'
Requires-Dist: pytest-cov>=5.0; extra == 'dev'
Requires-Dist: pytest>=8.0; extra == 'dev'
Requires-Dist: ruff>=0.4; extra == 'dev'
Provides-Extra: macos
Requires-Dist: pywebview>=5.0; extra == 'macos'
Requires-Dist: rumps>=0.4.0; extra == 'macos'
Description-Content-Type: text/markdown

# Terminus Cancrorum Est

<p align="center">
  <strong><em>"The End of the Crab"</em></strong>
</p>

<p align="center">
  A macOS menu bar app + web dashboard + CLI for monitoring Claude Code processes, token usage, and costs.
</p>

<p align="center">
  <a href="https://pypi.org/project/tce-monitor/"><img src="https://img.shields.io/pypi/v/tce-monitor?color=c4a7e7&style=flat-square" alt="PyPI"></a>
  <a href="https://pypi.org/project/tce-monitor/"><img src="https://img.shields.io/pypi/pyversions/tce-monitor?color=89b4fa&style=flat-square" alt="Python"></a>
  <a href="LICENSE"><img src="https://img.shields.io/github/license/tmancino/Terminus-Cancrorum-Est?color=a6e3a1&style=flat-square" alt="License"></a>
</p>

---

## The Problem

Running multiple concurrent Claude Code sessions across many projects leaves you blind:

- **No process visibility** — How many Claude sessions are running? Which are stuck?
- **Zombie and stale processes** — Forgotten sessions silently consume hundreds of MBs
- **Token cost blindness** — Opus 4.5 costs $90/M output tokens. Costs compound invisibly across sessions.
- **No session history** — Which projects burned the most tokens today?

`tce` gives you real-time visibility into all of this from a single command, a menu bar icon, or a web dashboard.

## Install

```bash
pip install tce-monitor              # CLI + web dashboard (any platform)
pip install 'tce-monitor[macos]'     # + macOS menu bar + native webview window
```

Requires Python 3.11+.

## Quick Start

```bash
# See all your Claude processes right now
tce status

# Check how much you've spent
tce usage

# Kill all idle processes
tce kill-stale

# Launch the web dashboard
tce dashboard
```

---

## CLI Reference

| Command | Description |
|---------|-------------|
| `tce status` | Process health overview — PIDs, projects, memory, CPU, uptime, health status |
| `tce usage` | Token usage and costs — per-model breakdown with input, output, cache tokens |
| `tce sessions` | Recent session history — project, duration, tokens, lines changed, summary |
| `tce kill <PID>` | Kill a Claude process (SIGTERM). Add `--force` for SIGKILL |
| `tce kill-stale` | Find and kill all stale processes at once |
| `tce pin <PID>` | Pin a process — exempts it from stale detection |
| `tce unpin <PID>` | Remove pin from a process |
| `tce dashboard` | Start the web dashboard on `localhost:5111` and open in browser |
| `tce dashboard-stop` | Stop the running dashboard server |
| `tce run` | Full app — menu bar + dashboard (macOS) or dashboard-only (other platforms) |
| `tce install` | Install as macOS login service (auto-start at login via launchd) |
| `tce uninstall` | Remove macOS login service |

### Example Output

```
============================================================
 TERMINUS CANCRORUM EST — Process Status
============================================================
 Total: 7  |  Healthy: 4  |  Stale: 3  |  Zombie: 0  |  Pinned: 0
 Total Memory: 3449 MB
============================================================
 [+] PID  17742  rpgmaster                      6 MB    0.0%     6.9h  healthy
 [!] PID  31230  crab-trap                    392 MB    0.0%     6.8h  stale
              terminal: /dev/ttys002
 [+] PID  41126  openclaw                     219 MB    0.0%     1.4h  healthy
              terminal: /dev/ttys004
 [+] PID  59593  adventure-graph              953 MB    0.0%     2.3h  healthy
              terminal: /dev/ttys003
 [!] PID  85244  tweek-public                1167 MB    0.0%     6.1h  stale
              terminal: /dev/ttys007

 WARNING: 3 stale process(es) detected. Use 'tce kill-stale' to clean up.
```

```
============================================================
 TERMINUS CANCRORUM EST — Token Usage & Costs
============================================================
 Total Cost: $22,248.66
 Total Sessions: 183
============================================================
 Model                     Input     Output   Cache Rd   Cache Cr         Cost
 -------------------- ---------- ---------- ---------- ---------- ------------
 Opus 4.5                   2.9M       8.0M       7.4B     460.4M $ 20,318.33
 Opus 4.6                 392.0K     365.9K     734.6M      41.2M $  1,906.99
 Sonnet 4.5                 4.4K        655      23.6M       2.7M $     17.26
 Haiku 4.5                  5.7K       6.5K      31.4M       3.5M $      6.07
 -------------------- ---------- ---------- ---------- ---------- ------------
 TOTAL                      3.3M       8.3M       8.2B            $ 22,248.66
```

---

## Web Dashboard

Start with `tce dashboard` and open `http://localhost:5111`.

### Features

**Processes Tab**
- Live process table with color-coded health dots (green/yellow/red/blue)
- PID, project name, memory, CPU%, uptime, child process count, terminal
- One-click Kill, Force Kill, and Pin/Unpin buttons
- Status badge: "ALL HEALTHY", "STALE DETECTED", or "ZOMBIE DETECTED"
- Auto-refreshes every 10 seconds

**Token Usage Tab**
- Cost breakdown by model with color-coded bars
- Stacked bar chart of daily token consumption (last 30 days) via Chart.js
- Detailed token table: input, output, cache read, cache creation per model
- Total cost prominently displayed

**Sessions Tab**
- Recent sessions sorted by start time
- Project name, start time, duration, input/output tokens
- Lines added/removed (green/red)
- Session summary text

### Design
- Dark theme with monospace typography
- Tailwind CSS + Chart.js
- Sticky header with live status badge
- Responsive layout (2-6 column stat cards)

### API Endpoints

All data is available programmatically:

| Method | Path | Description |
|--------|------|-------------|
| `GET` | `/` | Dashboard HTML |
| `GET` | `/api/processes` | Process list (JSON) |
| `GET` | `/api/usage` | Token usage + costs (JSON) |
| `GET` | `/api/sessions?limit=20` | Recent sessions (JSON) |
| `POST` | `/api/kill/{pid}?force=false` | Kill a process |
| `POST` | `/api/pin/{pid}` | Pin a process |
| `POST` | `/api/unpin/{pid}` | Unpin a process |

---

## macOS Menu Bar

With `pip install 'tce-monitor[macos]'`, run `tce run` to get a persistent menu bar icon:

- **Menu bar icon**: Crab emoji that shows zombie/stale counts
- **Dropdown menu**: All processes with health icons, memory, uptime
- **Per-process actions**: Kill, Force Kill, Pin/Unpin
- **Open Dashboard**: Launch the web dashboard in a native webview window
- **macOS notifications**: Alerts when processes go stale or become zombies (with 30-minute cooldown)

The menu bar runs on the main thread (required by PyObjC) with the web dashboard on a daemon thread.

---

## Process Detection

Claude Code doesn't appear as `claude` in `ps aux`. Detection uses two strategies:

| Strategy | How |
|----------|-----|
| **Primary** | Executable path contains `.local/share/claude/versions/` |
| **Fallback** | `cmdline[0] == 'claude'` |

Both are checked per-process via `psutil`, with graceful handling of `AccessDenied` and `NoSuchProcess`.

## Health Classification

| Status | Icon | Criteria |
|--------|------|----------|
| **Healthy** | `+` / green | Running or sleeping, under all thresholds |
| **Stale** | `!` / yellow | Sleeping with <1% CPU for >4h (interactive) or >8h (background) |
| **Zombie** | `X` / red | Process in stopped (`T`) or zombie (`Z`) state |
| **Pinned** | `*` / blue | User-exempted from stale detection via `tce pin` |

Interactive vs. background is determined by whether the process has an attached terminal (`/dev/ttys*`).

## Data Sources

| Source | Path | What It Provides |
|--------|------|------------------|
| **Live processes** | `psutil` | PID, executable, cmdline, cwd, terminal, CPU%, RSS, children |
| **Stats cache** | `~/.claude/stats-cache.json` | Token counts per model, daily activity, session totals |
| **Session meta** | `~/.claude/usage-data/session-meta/*.json` | Per-session: project, duration, tokens, tools used, lines changed, summary |

Token data uses mtime-based caching — files are only re-read when modified.

## Model Pricing

Costs are computed from Anthropic's published pricing (per million tokens):

| Model | Input | Output | Cache Read | Cache Creation |
|-------|-------|--------|------------|----------------|
| Opus 4.5 | $15.00 | $75.00 | $1.50 | $18.75 |
| Opus 4.6 | $15.00 | $75.00 | $1.50 | $18.75 |
| Sonnet 4.5 | $3.00 | $15.00 | $0.30 | $3.75 |
| Haiku 4.5 | $0.80 | $4.00 | $0.08 | $1.00 |

---

## Configuration

Settings are loaded from environment variables (with `CLAUDE_MONITOR_` prefix) and `.env` files:

| Variable | Default | Description |
|----------|---------|-------------|
| `CLAUDE_MONITOR_PORT` | `5111` | Dashboard server port |
| `CLAUDE_MONITOR_HOST` | `127.0.0.1` | Dashboard bind address |
| `CLAUDE_MONITOR_PROCESS_POLL_INTERVAL` | `10` | Seconds between process scans |
| `CLAUDE_MONITOR_STALE_INTERACTIVE_HOURS` | `4.0` | Hours before interactive process is stale |
| `CLAUDE_MONITOR_STALE_BACKGROUND_HOURS` | `8.0` | Hours before background process is stale |
| `CLAUDE_MONITOR_STALE_CPU_THRESHOLD` | `1.0` | CPU% below which a process is considered idle |
| `CLAUDE_MONITOR_ALERT_COOLDOWN` | `1800` | Seconds between macOS alerts for same PID |

## Auto-Start at Login (macOS)

The easiest way to have TCE start automatically when you log in:

```bash
tce install
```

This creates a macOS launchd service that:
- Starts `tce run` (menu bar + dashboard) at every login
- Keeps the process alive (auto-restarts if it crashes)
- Logs to `~/.terminus-cancrorum-est/logs/`

To remove:
```bash
tce uninstall
```

### Manual launchd Setup

If you prefer to manage the plist yourself:

```bash
cp scripts/com.terminus-cancrorum-est.plist ~/Library/LaunchAgents/
launchctl load ~/Library/LaunchAgents/com.terminus-cancrorum-est.plist
```

To stop:
```bash
launchctl unload ~/Library/LaunchAgents/com.terminus-cancrorum-est.plist
```

---

## Claude Code Skill Integration

TCE includes a Claude Code skill so any Claude session can query your processes. Drop this project in your workspace and Claude will automatically use it:

```
You: "Check my Claude processes"
Claude: [runs tce status] → reports 7 processes, 3 stale

You: "How much have I spent on Claude?"
Claude: [runs tce usage] → $22,248.66 total, Opus 4.5 dominant

You: "Kill stale processes"
Claude: [runs tce kill-stale] → killed 3 processes
```

The skill is defined in `.claude/skills/terminus-cancrorum-est/SKILL.md`.

---

## Development

```bash
git clone https://github.com/tmancino/Terminus-Cancrorum-Est.git
cd Terminus-Cancrorum-Est
pip install -e ".[macos,dev]"

# Run tests
pytest tests/ -v --cov=tce

# Lint
ruff check tce/ tests/

# Type check
mypy tce/
```

### Project Structure

```
Terminus-Cancrorum-Est/
├── tce/                          # Installable Python package
│   ├── cli.py                    # CLI entry point (tce command)
│   ├── app.py                    # Full app: menu bar + dashboard
│   ├── menubar.py                # rumps macOS menu bar
│   ├── dashboard.py              # FastAPI web dashboard
│   ├── webview_window.py         # Native webview (macOS, optional)
│   ├── process_scanner.py        # psutil process detection + health
│   ├── token_tracker.py          # Stats cache + session meta parsing
│   ├── cost_calculator.py        # Token → USD pricing
│   ├── alert_service.py          # macOS notification alerts
│   ├── models.py                 # Pydantic models
│   ├── config.py                 # pydantic-settings configuration
│   ├── templates/
│   │   └── dashboard.html        # Tailwind + Chart.js dashboard
│   └── static/
│       └── logo.jpg
├── tests/                        # 50 tests (pytest)
│   ├── test_process_scanner.py   # Detection, health, pinning, scan, kill
│   ├── test_token_tracker.py     # Dashboard assembly, sessions, caching
│   ├── test_cost_calculator.py   # Pricing accuracy per model
│   └── test_models.py            # Pydantic serialization
├── scripts/
│   └── com.terminus-cancrorum-est.plist   # launchd auto-start
├── pyproject.toml                # Package metadata + tool config
├── LICENSE                       # MIT
└── README.md
```

### Architecture

```
tce run
├── Main thread: rumps menu bar [macOS only, requires pip install tce-monitor[macos]]
│   ├── Crab icon with zombie/stale badge
│   ├── Process dropdown with Kill/Pin actions
│   ├── "Open Dashboard" → native webview subprocess
│   └── macOS notification alerts (stale/zombie)
│
└── Daemon thread: FastAPI + uvicorn on :5111
    ├── GET /                  → Tailwind dashboard (Jinja2 template)
    ├── GET /api/processes     → ProcessScanner.scan()
    ├── GET /api/usage         → TokenTracker.get_dashboard()
    ├── GET /api/sessions      → TokenTracker.get_recent_sessions()
    ├── POST /api/kill/{pid}   → ProcessScanner.kill_process()
    └── POST /api/pin/{pid}    → ProcessScanner.pin()
```

On non-macOS platforms (or without the `[macos]` extra), `tce run` launches the dashboard on the main thread instead.

---

## Platform Support

| Platform | `tce` CLI | Web Dashboard | Menu Bar | Native Webview | Notifications |
|----------|-----------|---------------|----------|----------------|---------------|
| macOS | Yes | Yes | Yes (with `[macos]`) | Yes (with `[macos]`) | Yes |
| Linux | Yes | Yes | No | No | No |
| Windows | Untested | Probably | No | No | No |

---

## License

[MIT](LICENSE) — Tommy Mancino, 2026
