anthropics / anthropics/claude-code

Function hooks: an event when session usage or a rate-limit window changes, so trackers do not have to poll

Open
#94,424 1 comment 0 reactions 0 assignees View on GitHub
area:hooks enhancement
Dominant language
Python
Stars
145k
Forks
23.1k
PR merge metrics
PR metrics pending

Description

## What we are building

Three mods that keep session figures on screen (https://github.com/Arunjay4213/claude-mods): the context window fill, the 5-hour and 7-day plan windows with a reset countdown and burn rate, and a per-turn cost ledger. All three read `$.session.usage()`.

## The gap

`$.session.usage()` is a pull. Nothing tells a mod that the figures moved, so a live meter has to sample on `turn.complete` and on a `$.clock.every(60_000)` tick. Two things follow:

1. The countdown to a reset and a change in `percentUsed` reach the screen up to a minute late.
2. Every idle session runs a timer that mostly finds nothing changed, which is exactly the kind of busy work the hooks worker's budgets exist to discourage.

In #91870 the same ask was raised as "an event when a limit changes state (`{kind, percent, resetsAt}`)" and, after our mods landed, narrowed to "What remains of item 4 is an event when a threshold is crossed; today a quota guard has to poll" (https://github.com/anthropics/claude-code/issues/91870#issuecomment-5670691408). It has not been answered.

## Proposal

A `session.usage` event dispatched by core whenever the figures `$.session.usage()` returns would change: after each API response that carries `context` or `rateLimits`, and when a window resets. Input as the same `SessionUsage` shape, so a hook can write:

```ts
on('session.usage', ($, e, next) => {
const five = e.rateLimits.find(r => r.kind === 'five_hour')
if (five && five.percentUsed >= 90) $.ui.toast('5-hour window at 90%')
return next(e)
})
```

With that event a tracker needs no timer at all. The 60-second tick would still be wanted for a countdown that moves while nothing else happens, but it could then do no I/O.

## Two smaller things seen on 2.1.270 while building this

- `rateLimits[].percentUsed` arrives as floats such as `7.000000000000001`; whole numbers would match what the API means.
- After a window resets, `rateLimits` drops the window until the next API response. That is workable, but a note in the declarations would save the next person a surprise.

Claude Code 2.1.270, `CLAUDE_CODE_ENABLE_FUNCTION_HOOKS=1`, Linux.

Contributor guide

No contributing guide indexed for this repository

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.