[Bug]: Azure TTS rejects all non-Chinese voices — xml:lang is hard-coded to zh-CN
Bug Description
generateAzureTTS() in lib/audio/tts-providers.ts builds SSML with xml:lang='zh-CN' on both <speak> and <voice>, regardless of which voice the user selected:
// lib/audio/tts-providers.ts:657 (main @ 64621adf)
<speak version='1.0' xml:lang='zh-CN'>
<voice xml:lang='zh-CN' name='${config.voice}'>Azure validates that the SSML locale agrees with the selected voice and rejects the request, so only zh-CN voices can ever be synthesised. The Azure provider is therefore effectively unusable outside Chinese, even though both the provider catalog and the custom-voice settings invite the user to pick any Azure voice.
Steps to Reproduce
- Configure an Azure speech key and region.
- Select the Azure TTS provider.
- Set the voice to any non-Chinese voice, for example
en-US-JennyNeuraloren-ZA-LeahNeural. - Generate narration.
Expected Behavior
Azure synthesises the selected voice and returns audio.
Actual Behavior
The request fails because the voice does not match the SSML language, and no audio is produced. Every non-Chinese voice is affected — this is not limited to any one language.
Deployment Method
Local development (npm run dev / pnpm dev / yarn dev)
OpenMAIC Version
1.0.1 (64621adf)
Affected Area
Model / provider integration
Browser
Not applicable
Operating System
Windows 11 (app served from WSL2)
Relevant Logs
Azure TTS request failed: 400 — The language specified in the SSML is not supported
by the voice 'en-US-JennyNeural'.Additional Context
The locale is derivable from the voice name, which is already in BCP-47 form: strip the trailing Neural/MultilingualNeural segment and keep the remainder.
const voiceSegments = (config.voice ?? '').split('-');
const voiceLocale = voiceSegments.length > 1 ? voiceSegments.slice(0, -1).join('-') : 'zh-CN';This yields en-ZA-LeahNeural → en-ZA and sr-Latn-RS-SomeNeural → sr-Latn-RS. I have this working locally and am happy to open a PR if that would help.
Source: THU-MAIC/OpenMAIC