Context
web/src/hooks/browserLocalSpeech.ts gates the "Browser on-device" dictation provider (native window.SpeechRecognition) behind isConfirmedDesktopSpeechEnvironment(), which blanket-rejects mobile and unknown-UA browsers. The code comment explains why: some Android WebViews expose a partial SpeechRecognition shape whose available() call crashes the renderer, so the safe default became "desktop only."
Documented at docs/guide/voice-assistant.md:31.
Ask
Investigate whether this restriction is still necessary as a blanket policy, or whether it can be scoped more precisely (e.g. detect the specific broken WebView shape rather than reject all mobile/unknown UAs). Operator wants full parity across web — mobile should not be a second-class citizen for STT if it can be done safely.
Scope
- Reproduce or confirm the original crash report/motivation for the blanket restriction (git blame / PR history on
browserLocalSpeech.ts).
- Test actual behavior on real mobile browsers (Chrome Android, Safari iOS, common Android WebView versions) — does
SpeechRecognition.available() still crash, or was this fixed upstream in newer WebView versions?
- Propose either: (a) a safe way to detect and allow working mobile environments, or (b) confirm the blanket restriction is still the right call and document why more precisely.
- Do NOT implement the search-box long-press-to-talk feature — that is a separate peer/issue.
Not in scope
- Adding a new STT backend (native browser STT already exists and is shipped).
- The search-box UI work (tracked separately).
Context
web/src/hooks/browserLocalSpeech.tsgates the "Browser on-device" dictation provider (nativewindow.SpeechRecognition) behindisConfirmedDesktopSpeechEnvironment(), which blanket-rejects mobile and unknown-UA browsers. The code comment explains why: some Android WebViews expose a partialSpeechRecognitionshape whoseavailable()call crashes the renderer, so the safe default became "desktop only."Documented at
docs/guide/voice-assistant.md:31.Ask
Investigate whether this restriction is still necessary as a blanket policy, or whether it can be scoped more precisely (e.g. detect the specific broken WebView shape rather than reject all mobile/unknown UAs). Operator wants full parity across web — mobile should not be a second-class citizen for STT if it can be done safely.
Scope
browserLocalSpeech.ts).SpeechRecognition.available()still crash, or was this fixed upstream in newer WebView versions?Not in scope