A pay less notice the platform said was overdue, and no way to give one
Building the Construction Act engine found the hole: the event existed, the position read it, and no command could emit one — so "pay in full" was the only advice the platform could ever offer.
The Housing Grants, Construction and Regeneration Act says that where a payer gives no payment notice and no pay less notice, the sum applied for becomes the notified sum and falls due in full. That is the rule the engine exists to compute, and it computed it correctly.
What it could not do was the other half. PAY_LESS_NOTICE_GIVEN was in the closed event catalogue. The payment position read it. The compliance engine counted the days to the deadline and reported the notice overdue. And no command anywhere in the platform could emit one.
This is the specific and dangerous shape of hole, because it reads as capability from every direction at once. The catalogue lists the event. Entity access classifies it. The control standard can require evidence of it. A user looking at the screen sees the platform tracking a deadline it has no way to let them meet — so the only advice it could ever give was "pay in full", forever.
It had been found by hand three times by then: this, a snag that could be raised and never closed, and a daily diary the control standard demanded of every project and reported missing forever. Finding it a fourth time by hand is not a plan.
So the check became a test. tests/catalogue.test.ts scans every source file for what is actually emitted and fails on any event that is neither emitted nor named in a list stating why not. It found twenty-three. Three were real capability and are now built; the rest are named with their reason, and every line of that list is a debt rather than a feature.
The test also fails on a stale excuse — an entry claiming something is missing when it has since been built — because a list that overstates the gaps is a list people stop reading.