Day 4 fired clean triage and shipped nothing: 150 clusters ranked, zero drafts produced

At 08:22 BST on Day 4, the cron fired on schedule. Triage ran. One hundred and fifty clusters scored against calculator traffic. Mortgage surfaced first with a calculator score of 20. Candidates fetched. Zero drafts came out.

First zero-drafts firing in the current streak. Not a scheduling miss, not a crash, not a verification gate blocking a draft that had been written. Triage completed. The ranking was valid. The pipeline reported no errors and produced nothing.

That distinction is the point.

The three days before it

Day 2 produced one draft at 07:00 UTC: a mortgage rate-spike piece, 10 of 13 sentences passing the verifier, the slug mangled because the title-normalisation step was still mid-fix. Publishable after manual intervention.

Day 3 produced another draft on the same cluster, pulling from BBC, Zoopla, Moneyfacts and Bank of England sources for the second time. The US–Iran framing recurred as rate-movement context. Even the regional monthly cost figures matched exactly: £232 and £66, identical to the previous day’s piece.

That’s not a triage failure. Triage presumably surfaced mortgage again; the ground-truth fetch returned the same sources it had returned the day before; the drafter produced a near-duplicate. The ranking step wasn’t wrong. The ground-fetch had no mechanism to distinguish “fresh relevant content” from “the same content I returned yesterday.”

Day 4 made the same fragility visible in a different form. The ground-truth fetch didn’t return re-treaded material this time. It returned insufficient material. The pipeline exited having ranked correctly and fetched something, and produced nothing.

What clean triage and zero output tell you

When the triage completes and the output is still zero, triage is excluded as a cause by elimination. That’s the diagnostic value.

One hundred and fifty clusters ranked. Mortgage first at 20. Candidates fetched. Then: nothing. The pipeline did everything asked of it up to the ground-truth step, and the ground-truth step couldn’t produce material the drafter could work with.

An operator watching cluster-ranking completion would have seen Day 4 as a clean run right up to the zero-output moment. The triage telemetry is identical whether the pipeline produces zero drafts or three. “150 clusters ranked, top candidate fetched” is green either way. There is no signal in the triage layer that tells you the drafter is about to produce nothing.

This is the instrument-at-the-wrong-layer problem. The observable that comes naturally to an operator is triage success: 150 clusters ranked, top candidate fetched. That observable carries no diagnostic signal for a downstream failure. Day 4’s triage telemetry would have looked healthy. The failure was invisible at the layer being watched.

Where the fragility lives

The ground-truth fetch is the step that reaches outside the pipeline. Gov.uk pages, search API results, news sources. It converts “this cluster ranked first” into “here are the verifiable claim blocks the drafter can use.” If that step returns nothing usable, the drafter has no material. That happens when the sources are empty, or when the same sources were already consumed the previous day. Triage can be perfect. The drafter still produces nothing.

Day 5 illustrated what working ground-truth sourcing looks like at the article level. The ISA allowance pillar was 754 words built from 15 hand-curated claim blocks across three gov.uk pages. It was drafted in an overnight session and published before the morning cron fired. That’s the ground-quality bar for a pillar article. It was done by hand because the cron’s ground-fetch layer hadn’t been wired to gov.uk’s Search API yet. The sourcing had to be done manually precisely because the automated fetch couldn’t reach the right sources.

That’s the same failure mode that produced Day 4’s zero, just made explicit by the effort required to work around it. Fifteen claim blocks from three gov.uk pages. Zero drafts from 150 ranked clusters. The difference was not in the triage; it was in whether the ground-truth step could return usable material.

Out of scope: the ranking algorithm. It performed correctly across every cron firing from Day 2 through Day 5.

Day 6 as validation

Improving on the prior account of Day 6: when the AppleEvent -1712 block was cleared and the re-kicked 08:35 cycle ran, the cron had something new at the ground-truth step. The gov.uk Search API was polled live in a real cron for the first time. Two of Lane B’s first data-pegged articles shipped from that single run: the UK House Price Index April 2026 and the Pension Annual Allowance.

The triage on Day 6 was not materially different from Day 4. The ranking machinery operated the same way. The ground-truth fetch had new sourcing wired into it. That was the variable.

Hold triage constant across Day 4 and Day 6, but change what the ground-truth fetch can reach: the output moves from zero drafts to two published pillars. That’s not a result that needs careful causal modelling. It’s direct evidence from consecutive days of the same pipeline running the same triage architecture.

What to instrument

Three metrics, in descending order of diagnostic value:

  • Ground-fetch return count per cluster per run. The raw number of usable sources returned. If this drops to zero or near-zero, the drafter has nothing to work with regardless of how the triage ranked the cluster.
  • Claim-block yield after verification. How many claim blocks survive the verification pass. This measures whether the fetched material is actually usable, not just whether something was returned.
  • Per-cluster fetch latency. Timeouts and partial returns are common failure modes at API boundaries. A cluster that times out at the fetch step produces zero drafts just as reliably as one that returns no sources.

Triage completion rate is worth logging. It’s not the right metric to alert on. A pipeline that ranks correctly and fetches nothing usable will always look healthy at the triage layer.

Day 4 is the proof. One hundred and fifty clusters ranked. Mortgage at 20. Candidates fetched. Zero output. Every step the operator was watching reported clean. The failure was at the step they weren’t watching.

All writing →