diff --git a/cli-config.yaml.example b/cli-config.yaml.example index 932e99929019..4214e1b81696 100644 --- a/cli-config.yaml.example +++ b/cli-config.yaml.example @@ -1128,7 +1128,7 @@ stt: model: "base" # tiny | base | small | medium | large-v3 | turbo # language: "" # auto-detect; set to "en", "es", "fr", etc. to force # initial_prompt: "" # Optional faster-whisper prompt, e.g. bias Chinese output to simplified Chinese - # language: "" # GLOBAL language hint for every STT provider (per-provider language wins) + language: "en" # GLOBAL language hint for every STT provider (per-provider language wins). Set "" for auto-detect. # groq: # model: "whisper-large-v3-turbo" # language: "" # blank = stt.language > HERMES_LOCAL_STT_LANGUAGE > auto-detect diff --git a/hermes_cli/config.py b/hermes_cli/config.py index aab86489c4c6..ae5dc3626349 100644 --- a/hermes_cli/config.py +++ b/hermes_cli/config.py @@ -2323,8 +2323,11 @@ DEFAULT_CONFIG = { "echo_transcripts": True, "provider": "local", # "local" (free, faster-whisper) | "groq" | "openai" (Whisper API) | "mistral" (Voxtral Transcribe) | "elevenlabs" (Scribe) | "deepinfra" # Global language hint applied to EVERY provider unless a per-provider - # language overrides it. Empty = auto-detect. ISO-639-1 ("en", "es", ...). - "language": "", + # language overrides it. Defaults to "en" — Whisper auto-detection + # frequently misidentifies short/accented clips, which reads as + # "STT transcribed the wrong language". Set to "" to restore + # auto-detect, or to your language code ("es", "zh", "uk", ...). + "language": "en", "local": { "model": "base", # tiny, base, small, medium, large-v3 "language": "", # auto-detect by default; set to "en", "es", "fr", etc. to force diff --git a/tests/tools/test_stt_default_language.py b/tests/tools/test_stt_default_language.py new file mode 100644 index 000000000000..46545c375ed6 --- /dev/null +++ b/tests/tools/test_stt_default_language.py @@ -0,0 +1,33 @@ +"""Default STT language contract. + +Teknium (July 2026): the global ``stt.language`` DEFAULTS to "en" because +Whisper auto-detection frequently misidentifies short/accented clips +("STT transcribed the wrong language" class). Users opt back into +auto-detect with ``stt.language: ""``. +""" + +from hermes_cli.config import DEFAULT_CONFIG +from tools.transcription_tools import _resolve_stt_language + + +class TestDefaultSttLanguage: + def test_default_config_pins_english(self): + assert DEFAULT_CONFIG["stt"]["language"] == "en" + + def test_default_config_resolves_en_for_every_provider(self, monkeypatch): + monkeypatch.delenv("HERMES_LOCAL_STT_LANGUAGE", raising=False) + stt = DEFAULT_CONFIG["stt"] + for provider in ("local", "groq", "openai", "mistral", "xai", "elevenlabs", "deepinfra"): + assert _resolve_stt_language(provider, stt) == "en", provider + + def test_blank_global_restores_auto_detect(self, monkeypatch): + monkeypatch.delenv("HERMES_LOCAL_STT_LANGUAGE", raising=False) + stt = dict(DEFAULT_CONFIG["stt"]) + stt["language"] = "" + assert _resolve_stt_language("groq", stt) is None + + def test_per_provider_still_wins_over_default(self, monkeypatch): + monkeypatch.delenv("HERMES_LOCAL_STT_LANGUAGE", raising=False) + stt = dict(DEFAULT_CONFIG["stt"]) + stt["groq"] = {"language": "he"} + assert _resolve_stt_language("groq", stt) == "he" diff --git a/website/docs/user-guide/configuration.md b/website/docs/user-guide/configuration.md index c1981b0130de..5d1214e2c493 100644 --- a/website/docs/user-guide/configuration.md +++ b/website/docs/user-guide/configuration.md @@ -1713,7 +1713,7 @@ stt: enabled: true # Auto-transcribe inbound voice messages (default: true) echo_transcripts: true # Post raw transcripts back to the chat as 🎙️ "..." (default: true) provider: "local" # "local" | "groq" | "openai" | "mistral" - language: "" # GLOBAL language hint for every provider (ISO-639-1, e.g. "en", "he", "uk"); blank = auto-detect + language: "en" # GLOBAL language hint for every provider (per-provider language wins); set "" for auto-detect local: model: "base" # tiny, base, small, medium, large-v3 language: "" # per-provider override of stt.language @@ -1726,7 +1726,7 @@ stt: # model: "whisper-1" # Legacy fallback key still respected ``` -Language resolution is the same for **every** STT provider (local, groq, openai, mistral, xai, elevenlabs, deepinfra, command providers, and plugins): `stt..language` → `stt.language` → `HERMES_LOCAL_STT_LANGUAGE` env var → provider auto-detect. Setting `stt.language` once fixes the common "my voice notes get transcribed in the wrong language" problem regardless of which provider is active. +Language resolution is the same for **every** STT provider (local, groq, openai, mistral, xai, elevenlabs, deepinfra, command providers, and plugins): `stt..language` → `stt.language` → `HERMES_LOCAL_STT_LANGUAGE` env var → provider auto-detect. **The default is `stt.language: "en"`** — Whisper auto-detection frequently misidentifies short or accented clips, which shows up as voice notes transcribed in the wrong language. Non-English speakers should set `stt.language` to their language code once (e.g. `"es"`, `"zh"`, `"uk"`); set it to `""` to restore auto-detection for multilingual use. Set `stt.echo_transcripts: false` when the gateway should transcribe voice notes for the agent but must not post the raw transcript back to the chat (for example, customer-facing WhatsApp bots).