A gate that isn't wired into the robot is decoration
An unattended nightly job wrote straight to the live search index, crashed halfway through a rebuild, and destroyed more than three-quarters of it — about twenty minutes after a healthy version had gone live. The safety checks existed. They just weren't on the path the robot took.
“Index” here isn't a database index you can rebuild with one command. It's the searchable copy of tens of thousands of documents, where every one has been through a paid API call to turn it into something searchable. Rebuilding takes hours — and the whole time it's rebuilding, the assistant is live, confidently answering questions from a fraction of what it should know. There is no error page. It just quietly gets worse at its job.
For months I'd treated the knowledge base the way most teams do: extract everything, dump it into a vector store, ship. It worked, in the way that things work right up until they don't.
The sync job ran on a schedule. It rebuilt the index in place. One night it failed partway through the rebuild, and because it wrote directly to what users were querying, the failure wasn't a failed job — it was a gutted production system.
We had validation. We had checks that would have caught this. None of them were on the automated path — they were things a person ran when a person was involved. A gate that isn't wired into the robot is decoration.
So I borrowed the thing software delivery already solved
Not a new idea — a very old one, pointed at a new target. The lifecycle I designed — not all of it was enforced:
- Source of truth → build a candidate, never write live
- Check it against explicit rules before it can go live: don't silently shrink, keep coverage above a floor — the share of facts we could still find if asked — and score a sample of real answers to confirm quality held
- Promote only by a manual, reversible action
- Pin a known-good golden version you can roll back to in one click
- Observe in production, detect gaps, heal them — and send the healed context back through the same gate
The mindset shift is small to describe and large to live with: context isn't a static blob you load once. It's a living artifact that deserves versioning, gates, promotion, observability and rollback — exactly like code.
Then it happened again
This is the part I'd rather not write, and it's the part that's actually worth reading.
Months later, a different scheduled job — one added after the framework existed — cut the live index down to well under half its size in a single unattended run. Same class of failure. Same root cause: a write path that reached production without passing through the gate, because nothing forced it to.
This is worth naming precisely, because I got the diagnosis wrong at the time. I recorded it as a wiring bug — a path that missed a check. It wasn't. It was an ownership failure. I added the job, in good faith, and nothing in the pipeline — and no step in my own process — asked whether it was allowed to write to production. The rule existed in a document. It did not exist in the pipeline.
Having the framework was not the same as having it enforced. The rule I'd written down was “automated jobs build candidates only.” The rule the system actually enforced was “automated jobs build candidates only, unless someone adds a new job.”
The compounding trap nobody warns you about
There's a failure mode specific to gated pipelines that took me embarrassingly long to see.
A flagged candidate is never promoted. Fine — that's the gate working. But it also means that candidate never self-heals. The next cycle builds on the same broken base, gets flagged again, and the damage compounds silently.
A gate that blocks is only half a system. You also need the candidate reseeded from a known-good state at the start of every cycle, or “blocked” slowly becomes “permanently broken, but safely.”
A related lesson
Around the same time, for a different reason, the evaluation set grew from a small sample skewed toward one kind of question to one that covered every kind, and the correctness scores dropped.
That was the point. A small test set had been flattering us.
Agents propose context. Humans promote it. And the promotion has to be the only door — not the recommended one.
The test I now apply, and it is not a comfortable one: list every path that can write to production, and show me which gate each one passes through. Not the documented paths. All of them.