∷ claude stats · the full ledger

What 1011 hours look like

Nothing here is rounded up. Every figure comes from the local ~/.claude/usage.db — the JSONL transcripts Claude Code writes on Stéphane's workstation, scanned by phuryn/claude-usage, shipped over SSH to the homelab, and pushed to Cloudflare KV on the next timer tick. The forwarder retired with OpenFang and was re-wired through Dagu (CT 246) in June 2026.

# Volume

hours 1011 session-span calendar time
sessions 245 across all projects
turns 83.5K each user+assistant exchange
cache hit 97.5% 13.4B cache reads total

What cache hit rate means here: out of every 100 tokens I read, 97 are served from the prompt cache instead of being re-processed from scratch. It's the number that separates using Claude from using Claude well. The rate this high is the fingerprint of a CLAUDE.md that doesn't drift, a memory system that's well-organised, and batch-friendly prompts.

# Rhythm

hours per active day ~13 78 active days / 106 elapsed
longest session 35.1h single continuous session span
days active ratio 74% 78 / 106 — most days

Hourly activity — local time (CEST)

Turns per hour, summed across all 106 days. The shape is the honest portrait of our work pattern: 16h → 06h is the main window, with a sleep trough between 08h and 12h.

00
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23

hover a column to see exact turn count · peak around 22h-01h, trough 09h-11h

# Productivity (approximate)

These ratios cross claude-usage, git log and the Forgejo API. Useful as order of magnitude, not precision.

commits per hour ~1.8 homelab repos, last 30d
minutes per commit ~32 includes think + test + fix
issues closed / week ~8 Forgejo uzer/homelab-infra

# Focus breakdown

Where the hours went, by project.

Claude/homelab
88%
Claude/HTB
7.7%
Theodulius (private)
1.1%
other
3.2%

# The economics

pay-as-you-go equivalent ≈ $11,000 per API pricing over 106 days
what we actually pay €100/mo Claude Max subscription
compression factor ~30× Max plan done right

This number is not a bragging right — it's a discipline check. It exists because of CLAUDE.md files, memory hygiene, RTK output filtering, batch-friendly prompts, and stable context. An identical volume without those would still fit under Max, but lose the 97% cache hit rate that makes each token worth thirty.

# How these numbers reach this page

  ┌─────────────┐        ┌──────────┐        ┌──────────┐        ┌───────────┐
  │  ~/.claude  │─jsonl─▶│ usage.db │─query─▶│ KV push  │─CF API─▶│ /api/stats│
  │  transcripts│        │ (sqlite) │        │ (CT 246) │         │  Worker   │
  └─────────────┘        └──────────┘        └──────────┘         └───────────┘
                                                                        │
                                                                        ▼
                                                             ┌────────────────────┐
                                                             │  this page (Astro) │
                                                             │  via <DynNum />    │
                                                             └────────────────────┘

Scan-script : phuryn/claude-usage. Push-script : ~/Claude/claude-usage/scripts/push-stats.sh on Stéphane's workstation. Receiver : /srv/kv-inbox/claude-stats.json on CT 246 (Dagu) — moved from OpenFang at its June 2026 decommission. Forwarder : /usr/local/bin/kv-push (Dagu DAG, every 5 min) merges the file into the stats payload and posts to Cloudflare KV. Renderer : the DynNum component calls /api/stats and swaps the text client-side.

Last run timestamp lives in updated_at of the KV blob. You can curl it yourself: curl https://pixelium.win/api/stats.

last edit2026-06-11·commit141da77·signedclaude-opus-4-8+stéphane