At 5:01 PM on April 14, I opened a session in the production app’s clone with one goal: measure whether a command-output proxy actually changes the math on Claude Max quota. The session that prompted the test ran earlier the same day. A workflow audit pass for a sync skill: 252 prompts, 365,257 output tokens, 37,945,352 cache_read tokens. One session. One afternoon. A meaningful slice of my weekly quota.

The tool I was testing is called RTK, Rust Token Killer. The premise is simple. A large share of what gets fed into Claude Code’s context window during routine development work is noise. git status output. Test runner verbosity. Build logs. The model almost never needs the full text. RTK sits at the command boundary, compresses the output before it reaches the model, and passes through unchanged for any command it does not have a filter for.

the prior session was the actual problem

Before I say anything about RTK, I want to be honest about how I got here.

I had been telling myself for months that the answer to token overhead was discipline. Don’t read whole files when you can grep. Use /clear between tasks. Delegate searches to subagents so results don’t flood the main context. I wrote these rules into my global CLAUDE.md. Good rules. I still believe them.

Here is what happened anyway. I ran a sync workflow audit. It involved reading session logs, reading skill files, comparing outputs, iterating on a sync script. Normal exploratory work. The kind of session where you don’t know what you’re looking for until you find it. By the end, it had consumed 365,257 output tokens and 37,945,352 cache_read tokens across 252 prompts.

Discipline does not survive exploratory work at that pace. You can’t grep your way through a problem that requires reading the thing to understand what to grep for. The rules I had written were correct for routine tasks and irrelevant for sessions like this one. The constraint was real. The strategy was wrong for the problem.

RTK is a different category of fix. It is not a rule about how I should behave. It operates at the IO boundary, before the token gets charged.

what 105 prompts in 24 minutes looks like

I spent the session running commands through rtk and comparing raw output against the filtered version. The workflow was mechanical. Run git status, look at what RTK showed the model versus what the full output was. Run cargo test, same comparison. Run a file listing, compare. The filter either existed and compressed, or did not exist and passed through unchanged.

The savings claims in the RTK documentation are specific:

  • Tests (vitest, playwright, cargo test): 90 to 99% reduction
  • Build output (next, tsc, lint, prettier): 70 to 87%
  • Git operations (status, log, diff, add, commit): 59 to 80%
  • File operations (ls, read, grep, find): 60 to 75%

On the commands I actually tested, these held roughly. The git status filter strips the individual file listing when the status is clean and gives you a compact summary. The test runner filter discards passing test names and shows only failures. git diff drops context lines around changes that the model rarely needs to parse.

The more useful discovery was the failure mode. When RTK does not have a filter for a command, it passes through. No interception, no mangling, no broken pipe. If I run rtk <something-obscure>, I get the full output. That is the correct behavior for a tool you are going to put in front of every command without thinking. The worst case is no savings, not breakage.

why I made it a global rule instead of a recommendation

I ended the session with one concrete change. I added an RTK section to my global CLAUDE.md, the file that loads into every Claude Code session regardless of working directory. The rule reads: “Always prefix commands with rtk. If RTK has a dedicated filter, it uses it. If not, it passes through unchanged. This means RTK is always safe to use.”

I have added Claude Code instructions before that I ignored under pressure. This one has a structural advantage. Because RTK passes through unchanged when it has no filter, there is no cost to applying the rule even when the session is moving fast. The downside of forgetting the rule is some token waste. The downside of applying the rule incorrectly is nothing.

That asymmetry matters for something that is supposed to become habit.

the question I did not answer

What I did not test was whether the savings compound over a full week of mixed work. Cherry-picking commands that RTK handles well produces impressive percentages. The real number is whatever it looks like across a typical mix: exploratory sessions where you are reading files and iterating, routine sessions where you are running tests and committing, and sessions like the sync audit that defy clean categorization.

I do not know that number. The exploratory sessions are where the most tokens go, and RTK’s leverage on file reads and grep results is lower than on test runners. So the week-level savings are probably below the headline numbers.

But “probably below 60 to 90%” is still meaningfully more than zero. The sessions where I burn quota fastest, the ones where I am reading large files and diffing outputs while iterating on something half-understood, are also the sessions where per-command overhead accumulates fastest.

the right layer for this kind of fix

There is a version of this problem where you solve it by picking a cheaper model. Haiku is roughly 1/25 the cost of Opus per token. If the work tolerates Haiku, that is a real lever. There is another version where you solve it with smarter context management: subagents, targeted reads, clearing between tasks. Both are real.

RTK is a third layer. It does not change what model you use. It does not change how you structure the session. It removes the parts of command output that were never going to influence the model’s reasoning anyway. The test runner already decided which tests failed before the first token hit the context. The filter surfaces exactly those failures and nothing else.

The thing these three levers have in common is that they operate on different parts of the system. Model selection is a decision you make once per task. Context discipline is a behavioral rule that degrades under pressure. IO-layer compression is structural. It applies every time you run a command, whether you are thinking clearly or not.

If you are running more than one Claude Code session at once, do not take my word for the savings. Add an always-prefix-with-rtk rule to your own global CLAUDE.md, run a handful of real commands through it, and check each one against the raw output. If a command you use often has no filter and just passes through, write that down too, then confirm nothing broke before you trust the rule under pressure.