transcript_correction_enabled is not a pure cost lever: turning it off disables the noise gate and pushes over-merging #83

Open
opened 2026-08-27 02:50:30 -04:00 by logan · 0 comments
Owner

Found by the standing correlation pass on the unattended run of 2026-08-27, reviewing d18e4f0 before it shipped.

d18e4f0 put transcript correction behind a Firestore flag (transcript_correction_enabled) so that an "STT-only" evaluation window is actually STT-only and its spend can be attributed (#76, #45). That part is correct and the flag defaults to True.

The problem is that the flag is not what it looks like. It reads as a pure cost lever. It is not.

The coupling

The corrector is also the noise gate. It is the only thing that sets not_speech, and transcription.py returns None, [] for any call it flags. _is_degenerate is explicitly documented as catching a narrower set — two hard-coded repetition shapes — while the corrector catches novel ones.

With transcript_correction_enabled = false, not_speech is hard-coded False, so:

  1. Recogniser noise that only the corrector would have caught now reaches extract_scenes as a real transcript.
  2. It comes back with no units, no tags, no location, no severity.
  3. _is_thin_call is therefore True.
  4. The fast/thin path attaches it to the most recent incident on the talkgroup with no fit check (incident_correlator.py:962-970).

So correction off + correlation on pushes over-merging, via exactly the mechanism CORRELATION_REVIEW_0820.md named as mechanism A.

Why it was not fixed in the same commit

Splitting noise detection out of the corrector is a change to the transcription path, not to the flag plumbing #76 was about. Landing it inside an untested-against-live-traffic refactor of the spend gates would have coupled two risks that should be evaluated separately. The flag defaults to True and both flags are off in production, so nothing is currently exposed.

What to do

Short term, operational, and already written down: never open an evaluation window with correction off and correlation on. Recorded in DEFERRED.md and in the comment above the flag in feature_flags.py.

Long term: move not_speech detection out of transcript_correction.correct() so the noise gate survives the corrector being switched off. Then this flag really is a pure cost lever.

Refs #76, #45, #5. DEFERRED.md carries the matching row.

Found by the standing correlation pass on the unattended run of 2026-08-27, reviewing `d18e4f0` before it shipped. `d18e4f0` put transcript correction behind a Firestore flag (`transcript_correction_enabled`) so that an "STT-only" evaluation window is actually STT-only and its spend can be attributed (#76, #45). That part is correct and the flag defaults to True. **The problem is that the flag is not what it looks like.** It reads as a pure cost lever. It is not. ## The coupling The corrector is also the **noise gate**. It is the only thing that sets `not_speech`, and `transcription.py` returns `None, []` for any call it flags. `_is_degenerate` is explicitly documented as catching a narrower set — two hard-coded repetition shapes — while the corrector catches novel ones. With `transcript_correction_enabled = false`, `not_speech` is hard-coded False, so: 1. Recogniser noise that only the corrector would have caught now reaches `extract_scenes` as a real transcript. 2. It comes back with no units, no tags, no location, no severity. 3. `_is_thin_call` is therefore True. 4. The `fast/thin` path attaches it to the most recent incident on the talkgroup **with no fit check** (`incident_correlator.py:962-970`). So **correction off + correlation on pushes over-merging**, via exactly the mechanism `CORRELATION_REVIEW_0820.md` named as mechanism A. ## Why it was not fixed in the same commit Splitting noise detection out of the corrector is a change to the transcription path, not to the flag plumbing #76 was about. Landing it inside an untested-against-live-traffic refactor of the spend gates would have coupled two risks that should be evaluated separately. The flag defaults to True and both flags are off in production, so nothing is currently exposed. ## What to do Short term, operational, and already written down: **never open an evaluation window with correction off and correlation on.** Recorded in `DEFERRED.md` and in the comment above the flag in `feature_flags.py`. Long term: move `not_speech` detection out of `transcript_correction.correct()` so the noise gate survives the corrector being switched off. Then this flag really is a pure cost lever. Refs #76, #45, #5. `DEFERRED.md` carries the matching row.
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: logan/server-26#83