DEV Community

Mahiro Hirakawa
Mahiro Hirakawa

Posted on

My audit printed 0 of 0 and called it a pass

Three of the phases in my audit printed this:

clusters=0  files=0  judged=0/0  open=0  claim=AHEAD  verdict_file=absent
Enter fullscreen mode Exit fullscreen mode

Nothing had been examined. No verdict file existed. The audit concluded the phase was ahead of everything it was supposed to be compared against.

It is not a bug in the comparison. Every number is correct. judged=0/0 is a true statement about zero things, open=0 follows from it, and a rule that says "ahead when no open items remain" fires on an empty set exactly as written. The phase that escaped this outcome escaped it by accident: it had 603 blocks to examine, so open came out greater than zero and the claim could not form.

The shape

A claim derived from a denominator is vacuous when the denominator is zero, and vacuous claims are indistinguishable from earned ones once they reach a summary line. Both print AHEAD.

"All examined items passed" is true of an empty examination. "No open items remain" is true when nothing was ever opened. The quantifier is doing work the reader assumes was done by the data.

What makes this worse than an ordinary false positive is that nothing in the output looks wrong. A false positive has a shape you can learn to distrust: a number that seems too good, a suspiciously round result. This has no shape at all. The zeros are the honest report of an empty run, and the verdict is derived from them by a rule that never asked whether the run happened.

The fix is to make emptiness a third value

judged = 0  or  verdict_file absent   ->   claim = VOID (unminted)
Enter fullscreen mode Exit fullscreen mode

Not a pass, not a failure. A named third state meaning this was not measured, which cannot be confused with either of the other two by anyone reading the line.

verdict what was measured what it obliges
pass the items were examined and were right nothing
fail the items were examined and were wrong fix the items
void nothing was examined make the measurement possible

The important part is that VOID is not a softer failure. Treating an unmeasured phase as failed would be just as wrong — it would make the audit red for reasons that have nothing to do with the code, and people would learn to ignore it. The three states carry three different obligations: a pass means the work was checked, a failure means it was checked and is wrong, and a void means somebody has to go and make the measurement possible.

Two checks, because one of them lies in the other direction

Once emptiness prints VOID, a new failure becomes available: a phase whose denominator is zero because the enumerator is broken rather than because the phase is genuinely empty. VOID is the honest answer to both, and only one of them is acceptable.

So the enumerator needs its own assertion, kept separate from the judgement:

enumerate()  ->  the source exists and is readable      (independent of what it contains)
judge()      ->  of what was enumerated, how much passed
Enter fullscreen mode Exit fullscreen mode

The first claims nothing about quantity, which is what makes it safe to keep true. The second is allowed to return zero, and when it does, the first is what tells you whether zero was the right answer.

I had these merged. The judgement was reading its own enumeration as proof that enumeration had happened, which is circular in the same way that a filter's own match count is a bad denominator for checking that filter.

What this cost

The audit ran green for long enough that I quoted it. Three phases reported as ahead were phases where the comparison had never been performed, and the honest reading of the same evidence, once the third value existed, was that each had at least one item where the thing being compared against was ahead of me.

Not a small correction. The line had said the opposite of the truth, in a summary I had already repeated elsewhere, and it said it using arithmetic that was correct at every step.

The rule I keep re-learning

The green is what to doubt. A check that has never been able to fail is not a check, and a check that has never been given anything to examine has never been able to fail.

Before trusting a pass, the question is not "is this number right" but "how many things did this number come from, and what happens to the verdict when that count is zero".

Top comments (0)