Kannu
← Back to Kannu

How Kannu detects agent state

Kannu tracks five tools — Claude Code, Cursor, Codex, VS Code (Copilot) and Google Antigravity — and detects agent state through each tool's own integration, not by polling. In the tools with hook systems, Kannu registers a small script on six lifecycle events; when an event fires, the script writes a status file, Kannu watches those files, and the light in the notch updates. There is no timer scanning your processes, no log tailing loop, and it never reads your code.

Hooks, not polling

Polling asks "has anything changed?" on a schedule; hooks are told the moment it does. Because the agent tools themselves announce their transitions, the notch light changes within moments of the agent stopping or asking for approval — there is no polling interval to wait out, and no CPU spent checking on idle sessions. It also means detection accuracy comes from the tool's own event stream rather than from guessing at process or window state.

The six hook events

Kannu registers these events in each tool that exposes them:

Where the hooks are installed

Each tool keeps its hook configuration in its own file, and Kannu writes into it directly:

Each registered hook runs a small script that writes a status file for that session. Kannu watches the status files — that is the entire data path. If you uninstall Kannu, removing the hook entries restores each config to its previous behaviour.

What the lights mean

Internally an agent session is in one of five states — executing, thinking, awaiting input, stopped or inactive — which map onto three lights, named as the app's own Settings names them:

When the light appears

The light is a change notification, not a dashboard. On a notched Mac the island pulls itself into view when an agent changes state, holds for about seven seconds, then collapses on its own. Only real transitions bring it back — a running agent sends a heartbeat every couple of seconds, and that deliberately does not re-open the notch, otherwise the island would sit open for the whole run. Hovering the notch holds it open for as long as the pointer is there.

Making the lights readable

You pick each state's colour from a curated palette of ten hues, and two states can never share one — that constraint is what keeps the light legible if red and green look alike to you. The status indicator also carries a spoken, localized state for VoiceOver ("Agent status: needs your input"), so the signal is not colour-only. Two light styles are available: Classic keeps all three lights with the inactive two dimmed, Minimal shows only the one that is lit.

Several agents at once

Every session across all five tools appears in one list with its own state, and the notch shows exactly one light, aggregated across every running session: yellow beats green, so an agent blocked on approval surfaces above one that is happily working, and you never miss a waiting agent because a busy one is on top. Concurrent hook writes cannot silently downgrade the light — a parallel-write race that lost the urgent yellow in 11 of 200 rounds before the fix loses it in 0 of 200 after.

What it never touches

The hooks carry lifecycle events, not content. Kannu never reads your code, your prompts or your diffs. Credentials are used read-only — it never refreshes your rotating token, Keychain access sits behind an explicit one-time approval, and if a provider rate-limits it, it backs off. Beyond fetching your own usage figures from your own providers, there is no telemetry, no analytics and no backend of Kannu's own. The source is on GitHub under GPL-3.0 if you want to verify any of this yourself.