A tiny macOS menu bar app that keeps an eye on your Claude Code usage so you never get surprised by a rate limit again.
- 🟢 / 🟡 / 🟠 / 🔴 color-coded 5-hour session bar
- 🟢 / 🟡 / 🟠 / 🔴 color-coded 7-day weekly bar
- Hover → tooltip with exact reset times
- Click → popover with detailed breakdown (5h, 7d, Opus, Sonnet), reset timestamps, manual refresh, and inline preferences
- Reuses Claude Code's OAuth credentials from your login Keychain (no separate sign-in)
- Runs as a menu bar agent — no Dock icon, no window clutter
- Optional launch-at-login
Requires macOS 14+ and Claude Code installed and signed in. The app needs Claude Code's existing keychain entry to authenticate.
curl -L -o /tmp/ClaudeMeter.zip \
https://github.com/agencyenterprise/claude-meter/releases/latest/download/ClaudeMeter.zip \
&& ditto -x -k /tmp/ClaudeMeter.zip ~/Applications/ \
&& xattr -dr com.apple.quarantine ~/Applications/ClaudeMeter.app \
&& open ~/Applications/ClaudeMeter.appThis downloads the latest release, unzips it into ~/Applications, strips the
"downloaded from the internet" quarantine flag (the build is ad-hoc signed, not
notarized), and launches it. No auth needed.
- Go to https://github.com/agencyenterprise/claude-meter/releases/latest
- Download
ClaudeMeter.zip - Double-click to unzip → you'll get
ClaudeMeter.app - Drag
ClaudeMeter.appinto~/Applications(or/Applications) - Right-click → Open → Open (don't just double-click — Gatekeeper will block it the first time because the app isn't notarized). After this first "Open" it'll launch normally on every subsequent run.
- macOS will prompt: "ClaudeMeter wants to use the 'Claude Code-credentials' keychain item." → click Always Allow.
The icon appears in your menu bar with two thin bars next to the Claude logomark.
pkill -x ClaudeMeter; rm -rf ~/Applications/ClaudeMeter.app| Element | Where | Meaning |
|---|---|---|
| Claude logomark | left of bars | dimmed = refreshing / no data yet · full = data loaded |
| Top bar | menu bar | 5-hour session usage |
| Bottom bar | menu bar | 7-day weekly usage |
| Bar color | both bars | 🟢 0–50% · 🟡 50–80% · 🟠 80–95% · 🔴 ≥95% |
| Hover | menu bar item | tooltip with exact % and reset times |
| Click | menu bar item | popover with breakdown, refresh, prefs |
In the popover you'll also see the Opus and Sonnet weekly buckets if your plan has them.
Click the menu bar icon → "Preferences…" expands inline:
- Refresh interval — 1 / 2 / 5 minutes. Default 2.
- Launch at login — registers the app via
SMAppServiceso it appears in System Settings → General → Login Items.
Gatekeeper blocked the download. Run:
xattr -dr com.apple.quarantine ~/Applications/ClaudeMeter.appYour OAuth token in Keychain has aged out. Run any claude command in a
terminal — Claude Code refreshes the keychain entry on every invocation — then
click the ↻ refresh button in the popover.
You haven't signed into Claude Code yet on this machine. Run claude once, log
in, then relaunch ClaudeMeter.
The popover (click the menu bar item) has larger bars with exact percentages and reset times.
┌──────────────────────────────────┐
│ ClaudeMeter (LSUIElement agent) │
│ │
│ ┌───────────────────────────┐ │
│ │ UsageService (Timer) │ │
│ │ every 2 minutes │ │
│ └─────────────┬─────────────┘ │
│ │ │
│ reads OAuth │ │
│ token from │ │
│ Keychain │ │
│ "Claude Code-credentials" │
│ │ │
│ ▼ │
│ GET api.anthropic.com │
│ /api/oauth/usage │
│ Authorization: Bearer <token> │
│ │ │
│ ▼ │
│ decode { five_hour, seven_day, │
│ seven_day_opus, ... } │
│ │ │
│ ▼ │
│ ┌──────────────────────────┐ │
│ │ MenuBarExtra │ │
│ │ ✦ ▓▓▓▓░░░░░░░░ ← 5h │ │
│ │ ▓▓░░░░░░░░░░ ← 7d │ │
│ └──────────────────────────┘ │
└──────────────────────────────────┘
The endpoint is the same one Claude Code's /status command calls — the numbers
match exactly.
You only need this if you're hacking on the app itself.
- macOS 14+
- Swift 6 toolchain (Command Line Tools is enough — Xcode not required)
xcode-select --install
git clone https://github.com/agencyenterprise/claude-meter.git
cd claude-meter
make install # builds .app, installs to ~/Applications, runs codesign
open ~/Applications/ClaudeMeter.app| Target | What it does |
|---|---|
make app |
Build build/ClaudeMeter.app (release) |
make install |
Build and copy to ~/Applications/ClaudeMeter.app |
make run |
Build and open the bundle |
make release |
Build + zip into build/release/ClaudeMeter.zip |
make uninstall |
Kill the running app and remove it from ~/Applications |
make clean |
Remove build/ and .build/ |
swift run ClaudeMeter --print-token-shape # shape of the keychain blob (no secrets)
swift run ClaudeMeter --print-usage # raw JSON from /api/oauth/usage
swift run ClaudeMeter --print-usage-typed # decoded into Swift valuesPackage.swift # Swift Package Manager manifest
Makefile # build / app / install / release / clean
Resources/
Info.plist # LSUIElement=YES, bundle metadata
Sources/ClaudeMeter/
main.swift # entry point + diagnostic CLI flags
ClaudeMeterApp.swift # SwiftUI App scene + MenuBarExtra wiring
MenuBarLabel.swift # NSImage rendering of bars + Claude logomark
PopoverView.swift # popover content + inline preferences
UsageService.swift # ObservableObject, polling Timer, LoadState
UsageAPI.swift # URLSession call to /api/oauth/usage (host fallback)
UsageModels.swift # Decodable Usage / Bucket (defensive optionals)
Keychain.swift # SecItemCopyMatching wrapper
LoginItem.swift # SMAppService toggle for launch-at-login
Resources/
claude-color.svg # official Claude logomark
- Bump
CFBundleShortVersionStringandCFBundleVersioninResources/Info.plist. make release→ producesbuild/release/ClaudeMeter.zip.git tag vX.Y.Z && git push --tagsgh release create vX.Y.Z build/release/ClaudeMeter.zip --title "vX.Y.Z" --notes "..."
- macOS only (the Claude Code keychain entry only exists on Mac).
- Ad-hoc signed, not notarized — needs the quarantine workaround on first install. If we want to ship a notarized build, we need an Apple Developer ID.
- App can't refresh expired OAuth tokens on its own — it leans on Claude Code
rewriting the keychain entry on every
claudeinvocation. In practice this is fine; tokens last long enough that you'll touch the CLI before expiry. - The
/api/oauth/usageendpoint is undocumented and could change without notice. The decoder treats every field as optional so a schema change degrades to a dash rather than crashing.
Ideas for later:
- Native notification when 5h or 7d crosses 80% / 95%
- Sparkline of the last few days
- Optional total-cost mode (using
~/.claude/stats-cache.json) - Homebrew tap for one-line install via
brew install
Internal AE tool. Do whatever you want with it inside the company.