Spend · Subscription seats
Subscription seats
See it in motion
Where to find it
- Localhost:
/seat-truth.html?repo=<id> - API:
GET /api/seat-truth?repo=<id>&window=<days> - Sidebar: Spend Telemetry Subscription seats
- Keyboard: ⌘ K then
telemetry, then pick the Subscription seats subtab
Set it up
One half of this cannot be discovered by any machine, so you enter it. Add your subscriptions under subscriptions in the repo's account settings: vendor, plan, seat count, monthly price, currency, renewal date, and a roster of the identifiers your captured sessions carry. Price and roster are both optional. Without a price you still get the usage answer; without a roster you get the totals but no per-seat rows.
The activity half needs no setup beyond the capture you already run. This works on metadata-mode capture: knowing that a conversation happened, under which account, at which time answers the question, and no prompt or answer text is read for any of it.
What a row tells you
The claim this page refuses to make
A seat RepoOps captured nothing for is not an unused seat. The person may work through a corporate account RepoOps cannot see, have the browser extension switched off, or be on leave. A renewal decision made on a mislabelled row takes a working tool away from a real person, and they will be told a number caused it.
So such a row reads no activity captured, and carries both why it might be quiet and what would settle the question. That wording is produced in one place in the code and rendered verbatim everywhere else, and tests assert the word “unused” appears nowhere in the data, the page, or the export.
Three pairs of numbers that look alike
- Seats bought is not the roster. A seat nobody was assigned is counted on its own: nobody can be using it, and nobody has been told it exists either.
- Captured sessions is not sessions matched to a seat. The unmatched ones are reported rather than dropped, because dropping them makes every seat read quieter than the capture was.
- The monthly price is money that left the bank. Everything derived by dividing it carries amortized in its name and never the word cost.
The renewal review
A renewal is decided in a meeting, from a file, weeks after anybody looked at a tab. The two download buttons produce that file as Markdown or CSV. It is dated, it names the window it was measured over, and it lists every seat with nothing captured plus every seat captured once or less.
The generated date and both ends of the window are the first three columns of the CSV, on every row, not a header block. A spreadsheet reader sorts, filters and pastes rows out of context within a minute of opening a file, and a seat number that has lost its period is the mistake this whole feature exists to prevent.
The dollar figure on the review is what the bill attributes to those seats. It is not what cancelling them would save, and the file says so in those words: some of them are in use through a path RepoOps cannot see, and per-seat plans rarely refund by the seat.
Honest limits
- It reports what RepoOps captured. Coverage depends on where your team works and what capture is switched on, and a gap in coverage looks exactly like a quiet seat until you check.
- The roster is identifiers, not people. It matches whatever string your captured sessions carry as a user id. A person whose seat is registered under a different identifier reads as two facts: a quiet seat, and unmatched sessions.
- Rosters go stale. Seats bought and seats rostered are kept separate for that reason, and the difference is shown rather than reconciled for you.
- A subscription with no price answers usage only. No price means no per-seat figure, and the page says “not stated” rather than 0.00.
Read more
- Activity ledger: per-developer session timing from Claude Code telemetry.
- Metered spend: real metered LLM spend, which a flat subscription is not.
Last updated