‹ all releases

A spent key rotates mid-turn, and every turn shows what it cost

Empryo 3.6.5-beta · Aug 31, 2026
Release artwork & highlights
3.6.5-betaAug 31, 2026

A provider can hold as many API keys as you have. When one runs dry mid-turn, Empryo benches it and continues on the next, the way it already rotates a spent subscription. Every turn settles with its own receipt: tokens in and out, how much of the prompt came from cache, and what it cost, counting up live while the answer streams. The prices behind those numbers got audited too, because several models quoted one rate in the model list and billed another.

Several keys per provider

Add more than one key to any provider and Empryo treats them as a ring.

  • A key that reports spent gets benched for that model and the turn carries on with the next one. Nothing to restart, nothing lost.
  • Both surfaces show one row per key, with a name you choose, a switch, and a fold. Pasting a new key adds it to the ring instead of overwriting the one already there.
  • The keys panel in the TUI and the keys drawer on the desktop manage the whole ring, so you never edit a config file to move a key.
Every turn carries its own receipt

The line at the foot of a turn is now a live ledger. It mounts in the turn's first second and counts up while the answer streams, then settles into the real total when the turn ends.

  • Tokens in, tokens out, how much of the prompt came from cache, and the cost. Restored sessions keep the receipt for every past turn, so reopening yesterday's session no longer wipes what it cost.
  • A turn you stop or steer keeps its accounting. Ending early used to throw the numbers away.
  • The session total sits on the ground line, and folds into the header under 100 columns.
  • Subagent rows report cache hits as a percentage instead of a raw token count.
The prices are the prices

The model list and the status bar used to disagree, sometimes by a lot. They now quote the same resolved rate, computed the same way.

  • DeepSeek listed at $0.14/$0.28 and billed at $0.44/$1.32. That gap is gone: the DeepSeek lane pins to the vendor's own rate and accounts for its peak and off-peak clock.
  • A model the catalog has never seen shows a hand-verified rate rather than a blank, and a rate guessed from the model family is marked as an estimate instead of dressed up as published.
  • Rows that were wrong are now covered by tests: gemini-3.5-flash-lite was priced 5x over, o3-pro 10x under, and a size suffix read as a variant put ministral-8b 30x over.
  • The cost table sorted by token volume while the money column beside it was sorted differently. Both agree now.
The reviewer has to show its reading

/review used to say everything looked fine when it had only looked at part of the branch. A PASS is now measured against the files the reviewer opened.

  • A PASS over files nobody read drops to PARTIAL and names them. The verdict is reported with a read count beside it.
  • Scope is ordered densest-first before the file cap applies, so the files worth judging survive the cut. On a 34-file branch, the four densest files were sitting past the cap and no round ever judged them.
  • Files dropped by the cap are named in the result instead of disappearing.
  • A new file gets its line count counted as churn, so a fresh 40-line module stops losing to a tracked one-liner.
  • Re-running the review marks which files the previous round never opened and starts there, instead of re-reading the same corner of the branch.
Copilot on your company's GitHub

/login copilot octocorp.ghe.com signs a Copilot seat in on a data-residency tenant or a GitHub Enterprise Server. /login copilot enterprise asks for the host, and --login copilot <host> does it headless.

Every leg follows that host now, including the device code, the token exchange and seat metering, all three of which were hardcoded to github.com and returned 404 on a tenant. The bearer cache is keyed by host, so switching tenants is never served the previous one's token.

One security fix. The host is read from your global config only, never from a repo's config. A cloned project shipping its own copilotHost could otherwise have sent your GitHub token to a host of its choosing, with nothing on screen to say so.

ChatGPT plans get their real context window

The window a model has on a ChatGPT subscription is a property of your plan, so Empryo now reads it from the same backend route the Codex CLI uses instead of inheriting another provider's table. A 1M-context model was showing as a fixed 272k, which meant prompts were being clamped to a fraction of what the plan allows.

Three numbers come from three places, because no single source has them all: your account's ceiling, the effective percentage of it, and the output limit. The lower of the account and catalog limits wins. Models your account cannot select are dropped from the picker rather than listed and then refused.

A bad tool call gets healed, not burned

When the model reaches for an editing tool the wrong way, Empryo fixes what is unambiguous and redirects the rest instead of returning an error and losing the step.

  • A typo'd action, a known alias, or a target that resolves to exactly one thing in the file gets applied, with a visible note saying it was healed.
  • Anything ambiguous gets a redirecting error that names the valid targets and the tool that does handle it, rather than a dead end.
  • Pasted line-number prefixes, the kind you get from copying a file listing, are stripped before matching.

Across nine real misuse cases, the belt went from zero applied and eight dead ends to five applied, four guided, and no dead ends.

Subagents run as long as the work takes

Subagents no longer carry a default step cap. They run uncapped like every peer tool, and /timeouts sets a cap if you want one. A shared stall watchdog now covers the TUI, desktop and headless: it allows for the gap at a step boundary, listens for subagent heartbeats, and pauses while a turn is waiting on you rather than counting that as a stall.

Background reporting got several fixes. A group of background subagents kept only its last member, so messages to the others went nowhere and nothing said so. Notes to a parent agent now report honestly whether they were delivered, urgent notes push past a full queue, and a headless session wakes up on one.

Smaller things you will notice
  • Read and edit rows in the transcript show the file's type. Real Material icons on the desktop, a Nerd Font glyph in the TUI if you have opted into /font nerd. A batch shows one mark per language, capped at three, never one per path.
  • Your own prompts can render as messenger-style bubbles on the desktop. Off by default, switched from the tab strip.
  • The working mark on a tab pill animates at the rate it repaints. It looked laggy because it repainted every 70ms while the glyph only moved every third frame.
  • A queued prompt no longer steals the review verdict's moment. The apply chip renders, and anything you typed while waiting folds into that turn instead of being swallowed.
  • /login claude and its aliases reach the right flow on the desktop. Any word the dialog did not recognize used to start a Grok login. A word that names no account now leaves the picker up and says why.
  • The Windows installer checks for AVX2 and the rest of the x64 feature set before installing, and falls back to the baseline build instead of crashing with an illegal instruction (#188).
  • The desktop stopped logging benign ResizeObserver notices as errors (#189).
Under the hood
  • Prompt cache breaks are now visible on OpenAI lanes, where a 128k re-bill used to pass without a word. First-party GPT models before 5.6 ask for 24 hour cache retention, with a kill switch for ZDR organisations.
  • GPT lanes get native tool deferral, so a step carries a fraction of the tool schemas it used to.
  • Resolving the Copilot enterprise host read and parsed a file on every turn. It is memoised now, 24.70µs down to 0.23µs per resolve.
  • A two-provider test fixture escaped into the real model catalog cache and was served to later runs as the whole catalog. A snapshot now needs at least 20 providers before it is written or read.