llm+rag: RAG-Pflicht fuer Wohnung/Immobilie/Kambodscha; generische Forced-Prompts

- _DOC_KW: wohnung, immobilie, condo, kambodscha, takeo, phnom, haus, ...
- Bei Geo/Wohnung: RAG-Query mit Zusatz-Keywords
- Forced-RAG: Finanz-Fokus vs. allgemeine Unterlagen (Gedaechtnis nicht Prioritaet)
- rag.py: Tool-Prompt Wohnungen/Ausland explizit
This commit is contained in:
Homelab Cursor 2026-03-26 18:53:06 +01:00
parent 84c6f97d35
commit 00283a6268
2 changed files with 71 additions and 5 deletions

View file

@ -428,6 +428,11 @@ def ask_with_tools(question: str, tool_handlers: dict, session_id: str = None, d
"lvm", "allianz", "ergo", "huk", "nuernberger", "lvm", "allianz", "ergo", "huk", "nuernberger",
"jahreskosten", "jährlichen", "jährliche", "jaehrlichen", "jaehrliche", "jahreskosten", "jährlichen", "jährliche", "jaehrlichen", "jaehrliche",
"monatliche kosten", "versicherungskosten", "beitragsrechnung", "monatliche kosten", "versicherungskosten", "beitragsrechnung",
"wohnung", "wohnungen", "immobilie", "immobilien", "mietwohnung",
"condo", "apartment", "eigentumswohnung", "häuser", "haeuser",
"haus ", " haus",
"grundstueck", "grundstück", "kambodscha", "cambodia", "takeo",
"phnom", "sihanouk", "siem reap",
] ]
_q_low = question.lower() _q_low = question.lower()
if route == MODEL_LOCAL and (document_mode or any(k in _q_low for k in _DOC_KW)): if route == MODEL_LOCAL and (document_mode or any(k in _q_low for k in _DOC_KW)):
@ -450,12 +455,48 @@ def ask_with_tools(question: str, tool_handlers: dict, session_id: str = None, d
question question
+ " Versicherung Beitrag Beitragsrechnung Jahresbetrag" + " Versicherung Beitrag Beitragsrechnung Jahresbetrag"
) )
elif any(
x in _q_low
for x in (
"wohnung",
"immobilie",
"condo",
"apartment",
"grundstueck",
"grundstück",
"kambodscha",
"cambodia",
"takeo",
"phnom",
)
):
_rag_q = question + " Wohnung Immobilie Mietvertrag Kambodscha"
_rag_finance_focus = any(
x in _q_low
for x in (
"kosten",
"beitrag",
"",
" eur",
"eur,",
"zahlung",
"versicherung",
"jähr",
"jaehr",
"jahreskosten",
"monatliche kosten",
"beitragsrechnung",
"preis",
"gebühr",
"gebuehr",
)
)
_rag_res = _rag_fn(query=_rag_q, top_k=60) _rag_res = _rag_fn(query=_rag_q, top_k=60)
if _rag_res and not _rag_res.startswith("Keine"): if _rag_res and not _rag_res.startswith("Keine"):
log.info("RAG-Pflicht: %d Zeichen — loesche Session-History", len(str(_rag_res))) log.info("RAG-Pflicht: %d Zeichen — loesche Session-History", len(str(_rag_res)))
messages = [ if _rag_finance_focus:
{"role": "system", "content": _full_prompt _rag_extra = (
+ "\n\nWICHTIG: Ignoriere fruehere Antworten. " "\n\nWICHTIG: Ignoriere fruehere Antworten. "
+ "STIL-OVERRIDE: Trotz globalem Hausmeister-Stil (kurz): diese Antwort bewusst etwas ausfuehrlicher " + "STIL-OVERRIDE: Trotz globalem Hausmeister-Stil (kurz): diese Antwort bewusst etwas ausfuehrlicher "
+ "(mehrere Saetze, Aufzaehlungen), damit Kosten und Zeitraeume ohne Nachfrage klar sind. " + "(mehrere Saetze, Aufzaehlungen), damit Kosten und Zeitraeume ohne Nachfrage klar sind. "
+ "Die Dokumentensuche unten ist die einzige Wahrheit. " + "Die Dokumentensuche unten ist die einzige Wahrheit. "
@ -472,14 +513,37 @@ def ask_with_tools(question: str, tool_handlers: dict, session_id: str = None, d
+ "wenn nicht erkennbar, ausdruecklich sagen. " + "wenn nicht erkennbar, ausdruecklich sagen. "
+ "VERBOTEN: Antwort nur als nackte Zahl (z.B. nur eine EUR-Zeile ohne Kontext). " + "VERBOTEN: Antwort nur als nackte Zahl (z.B. nur eine EUR-Zeile ohne Kontext). "
+ "Zu JEDEM Betrag mindestens einen Dateinamen aus den Treffern nennen. " + "Zu JEDEM Betrag mindestens einen Dateinamen aus den Treffern nennen. "
+ "Bei Kfz/Fahrzeug: sagen welches Dokument sich darauf bezieht oder dass die Zuordnung unsicher ist."}, + "Bei Kfz/Fahrzeug: sagen welches Dokument sich darauf bezieht oder dass die Zuordnung unsicher ist."
)
_rag_user_suffix = (
"\n\n[Strukturiert: Kurzfassung zu Jahr/jaehrlich, dann je Dokument Dateiname mit Betrag "
+ "und Zeitraum aus den Treffern; keine reine Ein-Zahl-Antwort.]"
)
else:
_rag_extra = (
"\n\nWICHTIG: Ignoriere fruehere Antworten und Priorisiere die Dokumentensuche unten "
+ "ueber Kurzinfos aus dem Gedaechtnis. "
+ "STIL-OVERRIDE: etwas ausfuehrlicher als sonst (Aufzaehlungen ok). "
+ "Die Treffer sind die einzige belastbare Grundlage. "
+ "Struktur: (1) Kurzfassung: was in den Treffern zur Frage passt. "
+ "(2) Je relevantem Treffer: Dateiname/Ordnerpfad und erkennbare Fakten aus dem Snippet "
+ "(Objekt, Ort, Datum, Parteien) — nichts erfinden. "
+ "Alle plausibel passenden Treffer nennen, nicht nur den ersten. "
+ "Wenn nichts passt: klar sagen dass die Suche nichts Relevantes lieferte."
)
_rag_user_suffix = (
"\n\n[Strukturiert: Kurzfassung, dann Liste je Treffer mit Dateiname und Fakten nur aus dem Snippet; "
+ "keine erfundenen Details.]"
)
messages = [
{"role": "system", "content": _full_prompt + _rag_extra},
{"role": "assistant", "content": None, {"role": "assistant", "content": None,
"tool_calls": [{"id": "forced_rag", "type": "function", "tool_calls": [{"id": "forced_rag", "type": "function",
"function": {"name": "rag_search", "function": {"name": "rag_search",
"arguments": json.dumps({"query": _rag_q, "top_k": 60})}}]}, "arguments": json.dumps({"query": _rag_q, "top_k": 60})}}]},
{"role": "tool", "tool_call_id": "forced_rag", {"role": "tool", "tool_call_id": "forced_rag",
"content": str(_rag_res)[:100000]}, "content": str(_rag_res)[:100000]},
{"role": "user", "content": question + "\n\n[Strukturiert antworten: Kurzfassung zu Jahr/jaehrlich, dann je Dokument Dateiname mit Betrag und Zeitraum aus den Treffern; keine reine Ein-Zahl-Antwort.]"}, {"role": "user", "content": question + _rag_user_suffix},
] ]
except Exception as e: except Exception as e:
log.warning("RAG-Pflicht Fehler: %s", e) log.warning("RAG-Pflicht Fehler: %s", e)

View file

@ -68,6 +68,7 @@ Du hast Zugriff auf eine private Wissensbasis mit >21.000 Dokumenten (Vertraege,
WANN rag_search AUFRUFEN IMMER bei diesen Fragen: WANN rag_search AUFRUFEN IMMER bei diesen Fragen:
- "habe ich..." / "gibt es..." / "wo ist..." / "finde..." / "zeig mir..." + Dokument/Vertrag/Versicherung/Bescheid - "habe ich..." / "gibt es..." / "wo ist..." / "finde..." / "zeig mir..." + Dokument/Vertrag/Versicherung/Bescheid
- Jede Frage nach persoenlichen Unterlagen, Vertraegen, Versicherungen, Rechnungen, Bescheiden - Jede Frage nach persoenlichen Unterlagen, Vertraegen, Versicherungen, Rechnungen, Bescheiden
- Wohnungen, Immobilien, Grundstuecke, Mietobjekte, Auslands-Objekte (z.B. Kambodscha): immer rag_search auch wenn das Gedaechtnis schon einen Wohnort nennt
- AUCH wenn du glaubst die Antwort zu kennen das Gedaechtnis ist NICHT die Wissensbasis! - AUCH wenn du glaubst die Antwort zu kennen das Gedaechtnis ist NICHT die Wissensbasis!
- AUCH wenn das Thema im Gedaechtnis steht trotzdem rag_search aufrufen fuer vollstaendige Antwort - AUCH wenn das Thema im Gedaechtnis steht trotzdem rag_search aufrufen fuer vollstaendige Antwort
@ -75,6 +76,7 @@ WANN NICHT: Nur bei reinen Homelab/IT-Fragen, Smalltalk, oder wenn der User expl
SUCHANFRAGE: Kurze Keywords, KEINE ganzen Saetze. Beispiele: SUCHANFRAGE: Kurze Keywords, KEINE ganzen Saetze. Beispiele:
- "Familienbuch" / "Grundsteuer Erklaerung" / "Haftpflicht" / "Kindergeld" / "Mietvertrag" / "Arbeitsvertrag" / "Reisepass" - "Familienbuch" / "Grundsteuer Erklaerung" / "Haftpflicht" / "Kindergeld" / "Mietvertrag" / "Arbeitsvertrag" / "Reisepass"
- "Wohnung Kambodscha" / "Immobilie" / "Condo"
ERGEBNISSE AUSWERTEN: ERGEBNISSE AUSWERTEN:
- Bei breiten Fragen ("welche Versicherungen", Jahreskosten, Listen): top_k=15-25, ALLE Treffer aus der Tool-Antwort abarbeiten - Bei breiten Fragen ("welche Versicherungen", Jahreskosten, Listen): top_k=15-25, ALLE Treffer aus der Tool-Antwort abarbeiten