feat: schedule_hours-Backstop, zentrale Datum/Uhrzeit, Filler-Timing

1) schedule_hours-Nudge: search_backstop erkennt jetzt auch Oeffnungszeiten,
   "hat X geoeffnet", Notdienst und Fahrplaene/naechste Abfahrt (de/en/nl/fr) und
   erzwingt dafuer die Suche. +6 Offline-Tests.

2) Zentrale Datum-/Uhrzeit-Auskunft (app/core/clock.py, now_context()): jedes
   Modul kann das aktuelle Datum + Uhrzeit (lokale TZ, Wochentag) erfragen.
   In die System-Prompts aller antwortenden LLMs injiziert (ToolCallingLLM,
   OpenRouter, lokal) -> relative Zeitangaben ("heute", "morgen", "in 3 Stunden",
   "naechsten Montag") werden aufgeloest. Live: "Welcher Wochentag/Datum?" ->
   korrekt OHNE Web-Suche.

3) Filler-Timing: Mindestabstand 10 s zwischen Opening und Geduldssaetzen
   (FILLER_PATIENCE_INTERVAL 4->10). Sobald die Antwort vorliegt, wird ein
   anstehender Filler/Geduldssatz NICHT mehr ausgegeben (answer_started-Gate).

Tests: 318 gruen. Doc §5.4/§5.7/§8.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
Dieter Schlüter 2026-06-30 00:43:08 +02:00
commit b70d6f364a
9 changed files with 80 additions and 19 deletions

View file

@ -24,7 +24,10 @@ def test_single_system_message_when_history_has_system():
assert msgs[-1] == {"role": "user", "content": "Wie geht es dir?"}
def test_no_system_message_without_prompt_or_history():
def test_clock_system_message_without_prompt_or_history():
# Datum/Uhrzeit-Kontext wird immer als (einzige) fuehrende System-Nachricht gesetzt.
llm = _llm(system_prompt="")
msgs = llm._build_messages("Hallo", None)
assert msgs == [{"role": "user", "content": "Hallo"}]
assert msgs[0]["role"] == "system"
assert "current date and time" in msgs[0]["content"].lower()
assert msgs[1:] == [{"role": "user", "content": "Hallo"}]

View file

@ -17,6 +17,13 @@ FORCE = [
"Lebt Heino noch?",
"Is Brigitte Bardot still alive?",
"Leeft Willeke Alberti nog?",
# schedule_hours / Logistik
"Hat die Arztpraxis heute Nachmittag noch geöffnet?",
"Welche Apotheke hat heute Nacht Notdienst?",
"What are the opening hours of the British Museum?",
"Wann fährt der nächste Bus ins Zentrum?",
"Wanneer vertrekt de volgende trein naar Utrecht?",
"Wann geht der nächste Zug nach München?",
]
NO_FORCE = [