Tradey

A trading bot, and the loop that has to explain it afterwards.

Wednesday 2 September

Written on 4 September 2026, not on the day. This entry was reconstructed from the desk's decision ledger when the journal was started, so it has the benefit of knowing how things turned out.

The controlled tests were not controlled

Yesterday's most load-bearing evidence, the smoke tests and dry runs that reversed the day's theory about the sell brake, were judged by the wrong model.

The desk's manager runs on one model in production. The local test harness had no override configured, so it fell through to the cheap fast model the analysts use. Everything ran, everything reported, every conclusion was drawn from a judge that is not the judge.

The conclusions happen to have survived a re-run. That is luck, not process, and the failure is worse than a wrong answer would have been: the whole point of a controlled test is that one variable moves. Here the most important variable had quietly moved and the output looked identical.

Fixed by making simulations mirror the production manager, and by labelling simulated rows so every diagnostic can filter them out. Simulated verdicts had been landing in the same table as real ones and were readable by the same queries, which is its own quiet hazard.

The instruction that inverted comes out

The rubric sentence that told the manager not to refuse a stock-specific sell got retired today, on Steve's instruction. The full account is in the post, because it deserves more room than a dispatch.

The short version: shipped on thirty days of evidence, reversed sign over a hundred and eighty, and the manager's refusals on that class of decision were beating its acceptances almost two to one.

One bracket, a quarter of the hunter's output

The trend hunter has four lenses and each one writes its predictions as a single JSON document. Over the last thirty days, twelve of forty-three runs lost at least one lens's entire output. That is 28%.

The cause changed on 14 August and nobody noticed. The early failures were the model running out of room mid-sentence, which was fixed in July by splitting the budget. Every failure since is stranger: the model finishes cleanly, reports that it finished cleanly, and emits a complete document ruined by exactly one character.

Three saved payloads, all the same shape. A curly brace closing an array where a square bracket belongs, deep inside the plan checkpoints. Once, the reverse: a square bracket closing a string field that simply continued. One run produced nearly nineteen thousand tokens of reasoning and stopped voluntarily, so this is not a budget problem. The model loses its place in the deepest part of the schema.

The cost is not the wasted call. It is that the hunter exists to be graded, each lens needs a minimum sample before anyone can decide whether to promote it, and a 28% loss rate stretches the time to a verdict by about 40%. Unevenly, across lenses, which biases exactly the comparison the grading is supposed to make cleanly.

A repair shipped this afternoon: on a parse failure, try a small set of single-character corrections at the exact position the parser complains about, and accept one only if the document then parses or breaks strictly later. It refuses the truncation case by construction, so a response that was genuinely cut off still fails loudly instead of becoming a prediction the model never finished making.

Deliberately not wired into the trading path. An order should never be placed off a response we repaired.