fix(llm): LLM antwortet jetzt in der konfigurierten Systemsprache

Bisher wurde `language` zwar an STT/TTS übergeben, aber nie an den LLM.
Lokales Modell antwortete deshalb immer auf Englisch/Deutsch, egal ob
Französisch, Spanisch o.a. eingestellt war.

Lösung: `language`-Parameter durch die gesamte LLM-Schicht gezogen:
- base.py: `lang_instruction()` helper + Signatur erweitert
- local_openai_compatible.py: Sprachanweisung ("Respond in Français.")
  wird als letzter System-Part in den Message-Stack eingefügt
- openrouter.py: Explizite Sprachanweisung ergänzt den bestehenden
  "Answer in the same language as the user"-Prompt
- fallback.py: FallbackLLMProvider leitet `language` durch
- orchestrator.py: alle 3 LLM-Aufrufstellen übergeben `language`
- Tests: alle Stub-LLMs um `language=None` ergänzt

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
Dieter Schlüter 2026-06-19 14:12:16 +02:00
commit 81d4cf6fd8
14 changed files with 89 additions and 44 deletions

View file

@ -37,11 +37,13 @@ class FallbackSTTProvider(_Chain):
class FallbackLLMProvider(_Chain):
async def complete(self, text, history=None, session_id=None) -> str:
async def complete(self, text, history=None, session_id=None, language=None) -> str:
last_exc = None
for index, (name, provider) in enumerate(self.entries):
try:
result = await provider.complete(text, history=history, session_id=session_id)
result = await provider.complete(
text, history=history, session_id=session_id, language=language
)
if index > 0:
self._on_fallback()
return result
@ -50,12 +52,14 @@ class FallbackLLMProvider(_Chain):
self._on_error(name)
raise last_exc
async def stream(self, text, history=None, session_id=None) -> AsyncIterator[str]:
async def stream(self, text, history=None, session_id=None, language=None) -> AsyncIterator[str]:
last_exc = None
for index, (name, provider) in enumerate(self.entries):
produced = False
try:
async for delta in provider.stream(text, history=history, session_id=session_id):
async for delta in provider.stream(
text, history=history, session_id=session_id, language=language
):
produced = True
yield delta
if index > 0: