An LLM that only gets paid when something is new.

Once a few automations were calling Claude on their own, the API bill was about to become the one line on the budget nobody could predict. I already pay for a Claude subscription. So I put two gates in front of every automated call: the model is only asked when there is something genuinely new to write, and wherever a machine is signed in to my plan, the call goes through headless Claude on that flat subscription instead of the meter. The pipeline stays AI-written. The cost became a number I set.

Elevated Trading · 2026 · Claude · Python · a Google Sheet as the cache · live in the 15-minute pipeline · ← all work

The problem

The product pipeline runs every fifteen minutes, all day. If each run asked an LLM to write copy for every product, that is thousands of calls a month for text that almost never changes, and a bill that grows with the schedule instead of the work. The easy answer was to not automate the writing at all, which is how most small companies end up with product pages that say nothing.

What I built

A description step with a free tier and a gate. A template writes a serviceable blurb for every product at no cost. The LLM is asked only for a product that is new, in stock, and has no copy yet, and its answer is stored in a sheet next to a column a human can overwrite. On machines signed in to my Claude plan, the call runs through headless Claude with the API key blanked, so it bills the subscription, not the meter.

What changed

The LLM runs a handful of times a month, once per new product, instead of ninety-six times a day. The bill stopped being open-ended: flat where a machine is signed in, a few cents on the smallest model where one isn't. Product pages ship with real copy on the same tick the product appears. And the gate turned out to be portable, so the same move now fronts three other automations.

Two gates, one picture

The first gate is about when. The second is about which door the call goes through. Almost every tick takes the top path and costs nothing.

The tick fires every 15 minutes, 96 times a day GATE 1 · WHEN A new in-stock item with no copy yet? both cells blank, nothing else counts no almost every tick Ship what's already there the human's override, if any else the copy written before else the free template $0 The product page on the same tick yes · a few times a month GATE 2 · WHICH DOOR Which machine is asking? A machine signed in to Claude runs headless Claude, and blanks the API key in that process first, so the call can only use the subscription flat · already paid · no meter The cloud VM, no sign-in a metered call, pinned to the smallest model; the same once-per-item rule still applies cents, not dollars One blurb, written once stored in a hidden sheet tab: Strain · Override · Generated · Updated never regenerated; the model only writes, every fact is handed to it next tick THE SAME GATE, DROPPED INTO OTHER AUTOMATIONS · headless Claude, key blanked, flat Meeting transcript → calendar + tasks a second pass re-reads knowing what the first caught Session memory extraction a hook that turns a work session into facts Lab-report extraction a PDF into a schema, replacing 13 regexes

Green is the path almost every tick takes. The purple boxes are the only places an LLM is ever invoked, and the left one is the trick: a signed-in machine with the key blanked cannot bill the meter even by accident.

The rules, in order of how often they fire

Why headless Claude is the interesting part

Claude can be run from a terminal without a conversation, a prompt in and an answer out. Run that way on a machine that is signed in to a subscription, it draws on the plan rather than the pay-per-token API, and the plan is a fixed number every month. The one thing to get right is that the same command will happily use an API key if it finds one in the environment. So the gate clears the key inside the child process before the call, every time. The metered path becomes impossible from that machine, not just avoided.

That turned the cost of automating with an LLM from an open-ended variable into a controllable one. A metered API on the loose bills for every run of every script that someone later wires up and forgets. A subscription with the meter unplugged bills the same whether the scripts run ten times or ten thousand. For a small company that is the difference between "let's automate that" and "let's not risk it".

Where the gate has gone since

The move is a few lines, so it became a module rather than a one-off. It now fronts a meeting assistant that reads a transcript and proposes calendar events and tasks, with a second headless pass that re-reads the transcript knowing what the first pass caught. It fronts a hook that turns a finished work session into searchable facts. And it fronts a lab-report extractor that reads a certificate of analysis PDF into a fixed schema, replacing a cascade of thirteen regular expressions, though that one is parked as a branch until the sheet it feeds is ready to switch over.

Where it stands

The description step has run in the 15-minute pipeline since July 2026, first against a local model on a Mac, since September against Claude on the production VM. The template tier, the once-per-item rule, and the override column are the parts that survived every backend change, which is the point of building the gate separately from the model behind it.

Stack

Claude (headless, subscription) Claude API (Haiku, metered fallback) Python Google Sheets API systemd timers a local model, earlier (Ollama)

The cheapest LLM call is the one you don't make. The second cheapest is the one already covered by a plan you're paying for anyway.

Built in conversation

Same method as everything on this site. The gate, the template engine's variation trick, and the override column all came out of dialogue with Claude, including the part where Claude helped design the thing that stops Claude from being called too often.

The philosophy, or what I'm building right now.