Skip to content

Reliability hardening: fix F-001, F-002, silent recording retention, CI security - #69

Merged
GalaxyRuler merged 20 commits into
mainfrom
codex/reliability-hardening-phase6
Jul 11, 2026
Merged

Reliability hardening: fix F-001, F-002, silent recording retention, CI security#69
GalaxyRuler merged 20 commits into
mainfrom
codex/reliability-hardening-phase6

Conversation

@GalaxyRuler

Copy link
Copy Markdown
Owner

Before Submitting This PR

Please confirm you have done the following:

  • I have searched existing issues and pull requests (including closed ones) to ensure this isn't a duplicate
  • I have read CONTRIBUTING.md

Human Written Description

I kept hitting reliability problems in real use — the push-to-talk toggle would stop working after the first dictation, locking a language sometimes produced nothing at all, and every so often a whole transcription just vanished at paste time with no error. Rather than patch each symptom, I ran a full audit of the pipeline and worked through the fragile spots end to end: capture, transcription, the language handling, the last-mile paste, the audio device layer, and the history/privacy path. This matters because a dictation tool that silently loses your words — or silently keeps a "deleted" recording on disk — is worse than one that fails loudly, and those silent failures were the pattern underneath most of the bugs.

Related Issues/Discussions

Bug-fix work (top priority per CONTRIBUTING). Addresses the internally-tracked F-001 (toggle-stop drops after the first cycle) and F-002 (locked-language dictation withheld/mistranscribed), plus a full-codebase assessment that surfaced two P0s (silent recording retention; an over-privileged manual CI build lane) and a weak merge gate.

Fixes #
Discussion:

Testing

Every change is TDD'd (test-first, red→green) and the full Rust library suite passes (645/645). Beyond unit tests, each area was device-verified on a real Windows machine with synthetic audio (VB-CABLE + SAPI TTS), reading ground truth from the history DB and app logs rather than trusting the UI:

  • F-001 toggle drop — 10 consecutive CLI toggle cycles + a rapid-toggle burst: 16/16 dictations landed with consecutive history IDs, zero drops, zero wedges.
  • Paste landing — verified real text lands in Notepad and the new verification correctly reports success (no false "paste failed").
  • F-002 locked language — locked English produces correct English on the real Whisper engine; locked Arabic no longer withholds output.
  • Audio robustness — dual-cpal runtime proven; mic-unplug mid-recording now stops in ~98ms instead of a 2s stall; cpal 0.17 device-name change caught and fixed so existing users' selected mic survives the upgrade.
  • Recording deletion (P0) — delete now removes the WAV before the DB row and keeps a retryable row on failure, so a "deleted" recording can never silently persist on disk; startup reconciliation cleans true orphans only.

Screenshots/Videos (if applicable)

N/A (backend/reliability changes).

AI Assistance

  • AI was used (please describe below)

If AI was used:

  • Tools used: OpenAI Codex (implementation, test-first) and Claude (planning, adversarial plan review, per-change code review, and the on-device QA harness/verification).
  • How extensively: Codex implemented each change against a reviewed plan; every change was independently code-reviewed and device-verified before inclusion. Findings from a full A–Z codebase assessment were verified against the source before acting.

What's in this PR (reliability train, reviewed commit-by-commit)

  • Pipeline wedge-killers (F-001): defer toggle presses that arrive mid-processing instead of dropping them; generation-tagged completion + stuck-pipeline watchdog; wall-clock timeouts on inference, model load, and LLM post-processing so a hang can never wedge the pipeline.
  • Last-mile paste: RAII clipboard-restore guard (original clipboard restored on every exit path); post-paste landing verification that drives success/recovery off what actually landed; pre-keystroke focus re-check.
  • Transcript quality (F-002): honor the locked language on Whisper; raise the language-guard floor so short correct output stops being withheld; gate dictionary fuzzy-replacements; validate remote LLM output (reject refusals/preambles/malformed envelopes to raw); classify empty-output-with-speech as a failure, not silence.
  • Audio robustness: surface device loss (no more 2s stall); VAD-init failure degrades to ungated capture instead of killing the mic; poison-tolerant locks + bounded waits; stable device IDs via cpal 0.17 with legacy-name compatibility.
  • Privacy + CI security: recording deletion can no longer silently orphan a WAV (P0); removed an over-privileged manual PR-build lane that ran contributor code with inherited secrets (P0); added a path-filter-free, read-only ci-required PR gate that actually builds + tests the app, and trimmed redundant push-to-main CI runs.

Note: after ci-required runs green here, it should be added to the main ruleset as a required check so this gate applies going forward.

🤖 Generated with Claude Code

GalaxyRuler and others added 20 commits July 9, 2026 13:07
… fix caseless uppercase bug

Update test_apply_custom_words_ngram_two_words to terminate at the replacement boundary. Its previous substring-only assertion accepted a greedy three-word replacement that consumed che and its comma, so it encoded corrupting behavior instead of the intended two-word correction.
…utput falls back to raw when speech observed
Disabled because untrusted PR code cannot safely reuse the privileged build workflow.
Require the exact ci-required context through branch rules so the policy check reports the live ruleset gap instead of querying the legacy branch-protection endpoint.

Add one path-filter-free Windows PR gate for backend checks and lib tests, frontend lint/typecheck/build, and deterministic Specta binding verification. The bindings exporter receives the common-controls manifest after linking, limiting the workaround to that executable and preserving the default Cargo test wrapper.
The pull_request event builds the test merge commit (PR head merged into
main), so a green PR already validated both jobs against main. The main
ruleset has strict=false and this is a solo repo, so a post-merge rerun is
near-pure duplication — and native-backend is the priciest job (macOS 10x +
Windows 2x whisper.cpp native compile). code-quality stays the required
check gating main; nix-check (packaging) and main-build (artifacts) are
unchanged. Direct pushes to main are lint-gated only — open a PR for native
+ test coverage.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 50f8ff3ff8

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

None
match selected_language {
"" | "auto" => None,
language => Some(language.to_string()),

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Normalize Chinese variants before passing Whisper hints

When the user locks dictation to Simplified or Traditional Chinese, selected_language is zh-Hans/zh-Hant and validate_selected_language accepts those because the Whisper catalog advertises them, but this new hint passes the raw BCP variant straight into Whisper. The provider already has normalize_language_for_engine() because the engine expects zh, so locked Chinese dictation can fail or lose the intended language lock after this change; return the normalized code here instead of language.to_string().

Useful? React with 👍 / 👎.

@GalaxyRuler
GalaxyRuler merged commit f3947a3 into main Jul 11, 2026
15 checks passed
@GalaxyRuler
GalaxyRuler deleted the codex/reliability-hardening-phase6 branch July 11, 2026 22:00
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant