Commit 39a9a46
committed
fix: bound the effective threshold, not one of its two handles (#134)
Verification found that bounding `tolerance` had closed one handle of a
two-handled lever and left the other free. The decision is
`actual - golden > tol`, so the gate passes anything at or below
`golden + tolerance` — that sum is the effective threshold, and the two
fields enter it identically. A golden of 2.0 with an honest tolerance of
0.02 admitted every physically possible error rate, and the tolerance
this same issue had just put on the passing line read a reassuring
0.0200, because the number that moved was not the one being rendered.
Reproduced against the real committed baseline with one field edited.
The bound is now on the sum (<= 0.5, against a committed maximum of
0.1749). It is the only bound invariant to trading one handle for the
other; a per-field bound always leaves its partner as a substitute.
`golden`'s own constant is deleted rather than kept. With the sum bounded
it can never be the guard that fires, and mutation testing put it at zero
failed assertions both before and after. A constant no test can
distinguish from its absence is not a guard. Its stated justification was
also wrong: "CER can exceed 1.0 via insertions" describes a measurement,
which ERROR_RATE_MAX governs.
A truncated comparison also still reported success. Closing the empty
case closed cardinality 0, not 1-of-N: both sides derive from the same
baseline.json, so deleting entries shrinks the baseline, the work list
and the measured set together and the gate prints "all 1 corpora within
tolerance" over a release that verified one twelfth of what it should
have — by pure deletion, with no unusual value anywhere. The expected
set is pinned in baseline-meta.json and, for the repo's own baseline, is
now an INVARIANT of regression-gate.sh: a missing, unreadable or
malformed meta is fatal there, an overridden BESTASR_BASELINE only warns.
The compare stage still tolerates an absent anchor with a printed NOTE,
because a stdin filter cannot know whether it was handed a whole sweep —
the invariant belongs where the answer is knowable. That conditional also
upgrades the #48 model-artifact pin, which was skipped SILENTLY when the
same file was missing.
A satisfied anchor now says so. Its only previous evidence was the
absence of the warning, which asks a reader to already know the warning
exists — the argument this issue makes for rendering the tolerance on
passing lines, applied to the guard it just added.
`error_rate: false` was the one boolean position still able to flip a
verdict, and nothing tested it: float(false) is 0.0, a boolean laundered
into a PERFECT SCORE rather than a bad one. Bounding golden at 0.5 had
quietly made the existing boolean test vacuous, which is the general
hazard — tightening one bound can hollow out another guard's only test.
OverflowError escaped the numeric converter; a bare 400-digit integer
parses to an arbitrary-precision int and float() raises neither TypeError
nor ValueError. Non-zero exit, so never a bypass, but it reached the log
as a stack trace where the verdict belongs. Rejected values are capped at
120 characters and corpus lists at 12 names, the anchor is shape-checked
before use, it names the file it actually read rather than the default
path, and the sum-bound message renders at 17 significant digits so a
rejected value cannot print as equal to the threshold it exceeded.
A second verify round found the anchor could still be switched off by
omitting a key, and that three guards had no test able to tell them from
their absence. The gate now REFUSES an unanchored run on the repo's own
baseline (missing, unreadable, or corpora absent/null/not a unique
non-empty string array); an overridden BESTASR_BASELINE warns instead.
The compare stage keeps tolerating an absent anchor with a NOTE, because
a stdin filter cannot know whether it was handed a whole sweep — the
invariant belongs where the answer is knowable, and both halves now have
a test so the permissive half is no longer the whole specification.
Every guard is non-vacuous, measured by deleting each independently:
sum bound 9, completeness 7, boolean 6, isfinite 5, TOLERANCE_MAX 3,
OverflowError 3, ERROR_RATE_MAX 2, echo cap 2, and the gate's own anchor
wiring 1 — a one-token typo in that shell heredoc used to revert the
whole completeness guard with a green suite, because nothing ran
regression-gate.sh.
Those counts come from scripts/mutation-check.sh, committed alongside
them. A count the reader cannot re-run is the same defect as a threshold
the reader cannot see, one level out.
The PR body has been regenerated from this tree. An earlier version of
this commit message claimed the body had already been corrected when only
the CHANGELOG had been; that claim was false when written and is the
reason this message was amended rather than followed by another commit.
474 tests / 88 suites green (+29 over main).
Refs #1341 parent 7c84d28 commit 39a9a46
6 files changed
Lines changed: 826 additions & 32 deletions
File tree
- Tests/BestASRKitTests
- benchmarks
- scripts
- lib
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
125 | 125 | | |
126 | 126 | | |
127 | 127 | | |
128 | | - | |
129 | | - | |
| 128 | + | |
| 129 | + | |
| 130 | + | |
| 131 | + | |
| 132 | + | |
| 133 | + | |
| 134 | + | |
130 | 135 | | |
131 | | - | |
| 136 | + | |
| 137 | + | |
| 138 | + | |
| 139 | + | |
| 140 | + | |
132 | 141 | | |
133 | | - | |
134 | | - | |
135 | | - | |
136 | | - | |
| 142 | + | |
| 143 | + | |
| 144 | + | |
137 | 145 | | |
138 | 146 | | |
139 | 147 | | |
| |||
155 | 163 | | |
156 | 164 | | |
157 | 165 | | |
158 | | - | |
159 | | - | |
160 | | - | |
161 | | - | |
| 166 | + | |
| 167 | + | |
| 168 | + | |
| 169 | + | |
| 170 | + | |
| 171 | + | |
| 172 | + | |
| 173 | + | |
| 174 | + | |
| 175 | + | |
| 176 | + | |
| 177 | + | |
| 178 | + | |
| 179 | + | |
| 180 | + | |
| 181 | + | |
| 182 | + | |
| 183 | + | |
| 184 | + | |
| 185 | + | |
| 186 | + | |
| 187 | + | |
| 188 | + | |
| 189 | + | |
| 190 | + | |
| 191 | + | |
| 192 | + | |
| 193 | + | |
| 194 | + | |
| 195 | + | |
| 196 | + | |
| 197 | + | |
| 198 | + | |
| 199 | + | |
| 200 | + | |
| 201 | + | |
| 202 | + | |
| 203 | + | |
| 204 | + | |
| 205 | + | |
| 206 | + | |
| 207 | + | |
| 208 | + | |
| 209 | + | |
| 210 | + | |
| 211 | + | |
| 212 | + | |
| 213 | + | |
| 214 | + | |
| 215 | + | |
| 216 | + | |
| 217 | + | |
| 218 | + | |
| 219 | + | |
| 220 | + | |
| 221 | + | |
| 222 | + | |
| 223 | + | |
| 224 | + | |
| 225 | + | |
| 226 | + | |
| 227 | + | |
| 228 | + | |
| 229 | + | |
| 230 | + | |
| 231 | + | |
| 232 | + | |
| 233 | + | |
| 234 | + | |
| 235 | + | |
| 236 | + | |
| 237 | + | |
| 238 | + | |
| 239 | + | |
| 240 | + | |
| 241 | + | |
| 242 | + | |
| 243 | + | |
| 244 | + | |
162 | 245 | | |
163 | 246 | | |
164 | 247 | | |
| |||
0 commit comments