Skip to content

fix(app): keep the transcript when diarization loses its audio - #565

Merged
pasrom merged 1 commit into
mainfrom
fix/diarization-failure-keeps-transcript
Aug 1, 2026
Merged

fix(app): keep the transcript when diarization loses its audio#565
pasrom merged 1 commit into
mainfrom
fix/diarization-failure-keeps-transcript

Conversation

@pasrom

@pasrom pasrom commented Jul 31, 2026

Copy link
Copy Markdown
Owner

Third defect from issue #558. Preparing the 16 kHz mix for diarization sat outside the block that treats a diarization failure as a warning, so a file problem there failed the entire job and threw away a transcript that was already finished.

Why the cost was wrong

By the time this step runs, transcription has completed and produced a non-empty transcript, which is where nearly all the compute went. Discarding it buys nothing: stage 3 already tolerates a missing mix, and nothing downstream of this particular failure needs one, because speaker naming is only ever parked when diarization actually produced speakers.

Moving the call inside the block makes a diarization problem cost the speaker labels and a warning, which is exactly what every other diarization failure already costs.

With that move, nothing in the stage can throw any more, so its signature no longer claims it can. That part is deliberate rather than tidying: the compiler now refuses the next throwing call someone adds outside the block, where a comment would only have asked politely.

Reachability

Only a paired source can reach this failure. A single-source job wrote its 16 kHz mix during transcription and the preparation step returns early, and because each run now owns its working directory, no sibling run can take that file away.

Evidence

The test drives a paired job whose sources are removed between transcription and diarization, which is a state a concurrent run relocating staged audio or a user tidying a folder can produce. It was watched fail first, with the real error the pipeline reports (com.apple.coreaudio.avfaudio error 2003334207), and it pins three things rather than one: the job reaches done, the warning is recorded, and the transcript exists on disk. Reverting the fix turns all three red.

Gates run locally: full test suite, SwiftFormat against the pinned version, SwiftLint, swiftlint analyze --strict with zero violations, and the release-mode parity build.

Known follow-ups, deliberately not in this change

  • The speaker labels are recoverable. Dual-track diarization reads the per-track 16 kHz files, not the mix, so in the only topology that can hit this failure the labels did not strictly have to die. The mix serves the output-folder sidecar and the naming dialog's playback. Preparing it lazily would downgrade the cost further, from "no speaker labels" to "no sidecar". This change is the minimal correct downgrade; that one is a larger rework of the stage.
  • Orphaned sidecars. On this path stage 3 now runs where the job previously died, so the per-track 16 kHz files and the segments JSON are persisted into the output folder with no consumer, since naming is never parked. The same already happens when diarization proper fails; this widens its reach.
  • Cancellation. The block's catch is untyped, so a cancellation landing inside it is downgraded to a warning instead of ending the job. That was already true for diarization proper; this adds the mix-preparation window to it.

Refs #558.

Preparing the 16 kHz mix for diarization sat outside the block that
treats a diarization failure as a warning, so a file problem there
failed the whole job. By then transcription has already finished and
produced a non-empty transcript, and that transcript was discarded
along with the minutes of compute behind it. Losing it buys nothing:
stage 3 tolerates a missing mix, and nothing downstream of this failure
needs one, since speaker naming is only ever parked when diarization
actually produced speakers.

Moving the call inside the block makes the cost proportional. A
diarization problem now costs the speaker labels and a warning, which
is what every other diarization failure already costs.

With that, nothing in the stage can throw any more, so the signature no
longer says it can. That is deliberate: the compiler now refuses the
next throwing call added outside the block, where a comment would only
have asked.

Only a paired source can reach this failure. A single-source job wrote
its 16 kHz mix during transcription and the preparation step returns
early, and since each run owns its working directory no sibling run can
take that file away.

Refs #558.
@github-actions github-actions Bot added the bug Something isn't working label Jul 31, 2026
@codecov

codecov Bot commented Jul 31, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 84.8%. Comparing base (76e942d) to head (50eea71).

Additional details and impacted files

Impacted file tree graph

@@          Coverage Diff          @@
##            main    #565   +/-   ##
=====================================
  Coverage   84.8%   84.8%           
=====================================
  Files        156     156           
  Lines      12358   12364    +6     
=====================================
+ Hits       10487   10495    +8     
+ Misses      1871    1869    -2     
Flag Coverage Δ
appstore 84.2% <100.0%> (-0.3%) ⬇️
audiotap 92.7% <ø> (ø)
homebrew 84.4% <100.0%> (+0.1%) ⬆️

Flags with carried forward coverage won't be shown. Click here to find out more.

Files with missing lines Coverage Δ
...tingTranscriber/Sources/PipelineQueue+Stages.swift 90.4% <100.0%> (+0.7%) ⬆️

... and 1 file with indirect coverage changes

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@pasrom
pasrom merged commit 0fa5d78 into main Aug 1, 2026
19 checks passed
@pasrom
pasrom deleted the fix/diarization-failure-keeps-transcript branch August 1, 2026 05:58
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant