Today the data is rendered to HTML, then scraped back out of that HTML, then rendered again. Every defect found this week lives in that round trip. This is what replaces it.
Data crosses a typed boundary once. Anything missing or mistyped stops there, loudly, instead of arriving as an empty value that reads like a quiet day.
The rendering stays ours, so Matt's approved design is untouched. What disappears is the layer in between.
None, which renders as absent, which reads as a quiet day.Found this week, all the same shape: a pattern stopped matching, returned nothing, and nothing was indistinguishable from nothing to report.
| What broke | How | Unnoticed |
|---|---|---|
| Abandonment guard | Upstream changed "aging 259d" to "open since April 2025". The pattern matched nothing, so the guard could not execute. | 18 days |
| New potentials section | Same dead field, second site. The error was caught and discarded, so every row fell through and the section never labelled. | 18 days |
| Caller time | Pattern expected the phone link before the name. Real markup puts the name first, so it never matched for a named caller. | unknown |
| Company goal check | Assertion matched HTML tags against text that had its tags stripped. It could never pass, and it blocked the send. | 1 day |
| Size guard | Examined whichever local folder sorted newest. Reported clean on data twelve days old. | unknown |
None of these failed loudly. A regular expression that stops matching does not raise an error; it returns nothing, and nothing looks exactly like a quiet day. A typed field cannot do that: it is present with a declared type, or the build stops and says which field is missing.
Today the send proceeds unless something interrupts it, so every failure is a stop that arrived too late. Inverting that makes lateness harmless.
The day's emails are rendered and checked. Nothing is addressed to anyone yet. This can happen as early as the data allows.
A person releases the day. Until that happens the mail does not go. No release, no send, and the miss is silent rather than damaging.
Brevo delivers. The release is recorded with who and when, so what went out is answerable afterwards.
A pause has to arrive before the send. A release has to arrive before the send too, but if it is late, nothing has gone. The failure mode moves from "mail went out wrong" to "mail did not go", which is recoverable within the hour and visible immediately.
These shape the work and none of them are engineering calls.
Njui emits data and we render, keeping Matt's approved design in our hands. Or Njui renders the final email and we only send, which removes our renderer entirely and moves design changes to his repo.
You, every morning. Or the reps release their own. Or an automatic release on a clean build with a human release required only when a check fails.
Today a known gap does not block a send. Under a contract, a field can be declared absent on purpose. Does a declared absence still send, and does an undeclared one stop everything.
Field by field, with both paths live and compared until they agree. Or a single switch on an agreed date. The first is slower and provably safe; the second is faster and trusts the schema.