從本地日誌估算 Claude Code「5 小時窗口」:AI Usage Gauge 的實作心得
Estimating Claude Code's "5-hour window" from local logs — what I learned building an always-on usage gauge
作者推出 AI Usage Gauge,一款 Windows 用量儀表,透過 Claude Code 本地日誌估算「5 小時窗口」的剩餘用量。
If you use Claude Code all day, you've probably been stopped mid-task by "usage limit reached". /usage tells you the official number, but only when you stop and ask. I wanted the answer to sit in the corner of my screen while I work, so I built a small Windows gauge that estimates what's left from the logs Claude Code already writes. This post is about how the estimate works.
1. What to read
Claude Code writes one JSONL file per session under ~/.claude/projects/<project>/<session>.jsonl. Assistant lines carry message.usage:
{"timestamp": "...", "message": {"model": "...", "usage": {
"input_tokens": 12, "output_tokens": 840,
"cache_creation_input_tokens": 3021, "cache_read_input_tokens": 98000}}}
The files are append-only, so I remember the last byte offset per file and read only what's new. Even with gigabytes of logs, each refresh costs almost nothing. It never reads login data or tokens.
2. What counts as "usage"
cache_read_input_tokens is huge (a long chat easily reads 100k+ per turn). Adding it in wrecks the estimate. I count input + output + cache_creation as usage and use cache_read only to judge how long a chat's context has grown.
3. Cutting the 5-hour windows
A window starts at the first request after the previous window ended, floored to the hour, and lasts 5 hours (an estimate that matches observed behaviour):
BLOCK = timedelta(hours=5)
def usage_blocks(events):
out = []
for ts, i, o, cc, _cr, _m in events:
if not out or ts >= out[-1][1]:
start = ts.replace(minute=0, second=0, microsecond=0)
out.append([start, start + BLOCK, 0])
out[-1][2] += i + o + cc
return out
4. Where does the limit come from?
Plan limits aren't published and change over time, so the gauge learns your limit:
- If you've ever hit the limit, the log has a "limit reached / resets …" line. The total of the window containing that moment is your measured limit.
- Otherwise, it uses your busiest 5-hour window in the last 31 days as a provisional ceiling ("headroom"). The 7-day limit works the same with a sliding window (the 7 days in progress are excluded).
Spend-limit lines are money-based, so they're ignored for learning.
5. "At this pace you'll run out around 6:30 PM"
From the last 30 minutes of usage it projects when you'll run out, and shows a yellow badge when you're going faster than your usual peak. It's not a perfect prediction, but knowing "about an hour left" before starting a big refactor has changed how I plan work.
6. Tkinter details
- Per-Monitor DPI v2, so it stays sharp on 125%/150% displays
- Tk's Canvas has no anti-aliasing, so rounded corners and bar ends are small images with per-pixel coverage
- Shipped as a single exe with PyInstaller
7. Other tools
The same approach reads Codex, Gemini CLI and Antigravity logs. Cursor doesn't store usage locally, so its tab only estimates activity from its chat database (opened read-only).
The tool
All of this is packaged as AI Usage Gauge (Windows, EN/JA/ZH/KO UI). 7-day free trial, then a one-time purchase.
https://github.com/aivex2024-spec/usagegauge
Unofficial, independent tool — not affiliated with Anthropic. Numbers are estimates. Feedback on the estimation method is very welcome.
來源:DEV Community · dev.to
