Expose `rate_limits` in hook payloads — statusLine-only delivery is unreachable from the desktop app
rate_limits ships and works. It just arrives on exactly one surface, and that surface doesn't
exist in the client I use.
I wrote the documented one-liner into my statusLine command:
printf '%s' "$in" | jq -c '{t:(now|floor), s:.session_id, rl:(.rate_limits // "ABSENT")}' >> "$HOME/.claude/rate-limits.jsonl"
Hand-fed a payload it appends correctly, exit 0. In a live desktop session the log file never
gets created — no statusline renders in the desktop app, so the command is never invoked. The
data is populated; there's no way to read it.
The gap is already in the tracker, closed unbuilt
#33820 asked for rate_limits in hook input and statusLine. It was closed as a duplicate of
#27915, which asked for statusLine only. #27915 shipped. The hook half was closed without ever
being built, and I can't find an open issue covering it. The related ones are all about
display: #74270 (glanceable by default), #65672 (monthly spend), #20636/#22428/#27915/#30784/#36056
(all statusLine, all satisfied).
What I'm actually trying to do
Record my weekly limit percentage at the end of each session, so I can see the slope instead of
guessing at it.
I already log per-session cost. That number can't see the week — I can be inside a perfectly
normal session and still two turns from a multi-day block. I hit a hard weekly block, lost some
work, and the only reason I know how close the next one is is that I ran /usage and pasted it
into a file by hand. Two data points isn't enough to tell a 1.2×/week trend from a 2×/week one;
four would be arithmetic.
/usage is fine for looking. It's not something a script can read.
Ask
Add rate_limits to hook payloads, same object and same optionality rules as the statusLine
field — absent for API key / Bedrock / Vertex, absent before the first API response.
SessionEnd is the one I need. UserPromptSubmit would be a bonus, since that's where a
threshold guard would live:
{
"hook_event_name": "SessionEnd",
"session_id": "...",
"transcript_path": "...",
"rate_limits": {
"five_hour": { "used_percentage": 50, "resets_at": 1780000000 },
"seven_day": { "used_percentage": 80, "resets_at": 1780200000 }
}
}
No new data, no new fetch — it's the same object the statusLine payload builder already spreads
in, handed to a surface that works outside the TUI.
Why not just use the statusLine
I would, if it ran. Two other reasons it's the wrong home for this even in the terminal:
- It fires on every paint, so anything durable means appending hundreds of lines a session and
taking the last one. A close event fires once.
- I assume it doesn't fire at all in headless
-pruns — I haven't tested that — which is where
unattended quota burn is least visible and most worth recording.
This issue has 1 comment on GitHub. Read the full discussion on GitHub ↗