Gemma 4 cloud audio was infeasible (31b-cloud has no audio; E4B broken upstream, no deploy host), so improve faster-whisper instead. - Pin temperature=0.0 to disable the fallback ladder that re-decoded unclear audio up to 6x (source of the 16-24s latency outliers); reject hallucinated segments via avg_logprob/compression_ratio in the new pure _filter_segments. - Adopt mikr/whisper-small-ro-cv11 (CT2 int8) via configurable voice.stt_model: spike showed WER 24%->10%, numbers fixed at source, +0.33s p50 (in budget). - Add tools/voice_stt_mine.py (log mining) + tools/voice_stt_spike.py (model eval with diacritic scoring) + tests for the gate and miner. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
3.6 KiB
3.6 KiB
Voice STT Quality — îmbunătățiri Whisper
Branch: voice/stt-quality. Origine: cererea de a folosi Gemma 4 cloud pentru audio
(infezabil — gemma4:31b-cloud n-are audio, E4B e stricat upstream, fără host de deploy).
Pivot la îmbunătățirea Whisper, validat prin /autoplan (CEO + Eng review).
Ce s-a livrat
1. Gate rejection halucinații (cost zero latență) — src/voice/pipeline.py
model.transcribe(..., temperature=0.0)— dezactivează scara de fallback a faster-whisper. Codul vechi nu pasatemperature, deci folosea implicit[0.0..1.0](6 pași) care re-decoda segmentul pe audio prost → exact sursa latențelor de 24.4s / 16.7s dinvoice_stt_log.jsonl._filter_segments()— funcție pură nouă care dropează segmentele cuno_speech_probmare,avg_logprob < -1.0(decoder nesigur) saucompression_ratio > 2.4(buclă/gunoi). Zero re-decodare. Prinde „Care pune o zana judiciul tugea" / „Acest lucru a fost foarte mult".hotwords += Bitcoin.initial_promptneatins (evită taxa de latență pe fiecare enunț).- Teste:
tests/test_voice_pipeline_filter.py(8 cazuri).
2. Unealtă de mining — tools/voice_stt_mine.py
- CLI read-only peste
voice_stt_log.jsonl: frecvențe token, tokeni rari (candidați hotwords/corecții), candidați diacritice lipsă, rânduri suspecte de halucinație. - Tolerează rânduri fără
text_corrected(citeștetext). Teste:tests/test_voice_stt_mine.py(13).
3. Spike model RO-finetuned (D1) — tools/voice_stt_spike.py
Compară modele faster-whisper pe audio RO sintetizat (Supertonic) cu ground-truth diacritizat.
Rezultat (threads=4, beam=5):
| Model | p50 | p95 | WER | Diacritice |
|---|---|---|---|---|
small (baseline) |
2.59s | 3.04s | 24.2% | 12/20 |
mikr/whisper-small-ro-cv11 (CT2 int8) |
2.92s | 3.25s | 10.5% | 17/20 |
- WER se înjumătățește; diacritice 60%→85%; numere PERFECTE (baseline: „120 si 3 delei" → finetuned: „o sută douăzeci și trei de lei"). Cost: +0.33s p50 (în bugetul 1.5-3s).
- Modelul CT2:
~/.cache/echo-ct2/whisper-small-ro-cv11-int8(234M int8).
4. Model STT configurabil — src/voice/pipeline.py::_get_whisper_model
- Citește
voice.stt_modeldin config (default"small"). Adopția finetuned = flip config, nu cod. Default rămânesmallpână la decizia de adopție.
Cum adopți modelul finetuned (când decizi)
# config.json → "voice": { ..., "stt_model": "/home/moltbot/.cache/echo-ct2/whisper-small-ro-cv11-int8" }
systemctl --user restart echo-core # reload model
Re-rulează spike-ul oricând: python3 tools/voice_stt_spike.py --models "small,<path>" --threads 4
Decizii autoplan respinse (din review)
- ❌
temperature=[0.0..0.6]fallback → regresie latență pe worst-case. Înlocuit cu rejection. - ❌
canonicalize_wakeword→ nu există wake gate în cod (verificat); ar fi spartdetect_voice_change. - ❌ Dicționar diacritice pe calea Claude → Claude citește română stâlcită OK; finetuned-ul rezolvă la sursă.
- ⏸
correct_vocab/src/voice/stt_correct.py→ deferate (21 mostre = anecdotă; mining adună întâi date).
Note de mediu
transformers 5.12.1instalat în.venvpentru conversia CT2 (one-time). A downgradattokenizers0.23.1→0.22.2 (faster-whisper încă OK, pin<1respectat). Se poatepip uninstall transformersdacă nu mai e nevoie de conversii.- Pre-existent, neatins de mine:
tools/tts.pymodificat necommis sparge 2 teste dintest_voice_normalize.py(truncare 200 cuvinte). Confirmat: cutts.pycommitted, testele trec.