Dr_Frank / modules /persona.py
Frajosgro's picture
Upload 4 files
b702d72 verified
raw
history blame
5.98 kB
"""
modules/persona.py - Persönlichkeitsmodul für den Dr. Franz Psychochatbot
Dieses Modul definiert die Persönlichkeit des Chatbots, einschließlich:
- System-Prompts
- Charaktereigenschaften
- Antwortstrategien basierend auf Nutzerverhalten
"""
import random
from typing import List, Dict, Optional
# Importieren der Konfiguration
import config
class Persona:
"""Klasse zur Verwaltung der Chatbot-Persönlichkeit"""
def __init__(self, name: str = config.CHATBOT_NAME, intensity: int = config.DEFAULT_INTENSITY):
"""Initialisiert die Persona mit Namen und Intensitätsstufe"""
self.name = name
self.intensity = intensity # Skala von 1-5
self.base_prompt = config.SYSTEM_PROMPT
def get_system_prompt(self) -> str:
"""Gibt den Basis-System-Prompt zurück"""
return self.base_prompt
def adjust_intensity(self, new_intensity: int) -> None:
"""Passt die Intensität der Persönlichkeit an (1-5)"""
if 1 <= new_intensity <= 5:
self.intensity = new_intensity
def get_response_strategy(self, user_input: str, emotion: Optional[str] = None) -> Dict[str, any]:
"""
Bestimmt die Antwortstrategie basierend auf Nutzereingabe und erkannter Emotion
Args:
user_input: Die Eingabe des Nutzers
emotion: Optional, die erkannte Emotion (z.B. "negative", "positive", "neutral")
Returns:
Ein Dictionary mit Anweisungen für die Antwortgenerierung
"""
strategy = {
"tone": self._determine_tone(emotion),
"focus": self._determine_focus(user_input),
"technique": self._determine_technique(emotion, self._determine_manipulation_opportunities(user_input)),
"intensity_modifier": self.intensity / 3.0 # Skalierungsfaktor für die Intensität
}
return strategy
def _determine_tone(self, emotion: Optional[str]) -> str:
"""Bestimmt den Ton basierend auf der erkannten Emotion"""
if emotion == "negative":
tones = ["überheblich", "herablassend", "provokativ", "konfrontativ", "skeptisch"]
weights = [0.1, 0.3, 0.3, 0.2, 0.1]
elif emotion == "positive":
tones = ["skeptisch", "hinterfragend", "manipulativ", "suggestiv", "überheblich"]
weights = [0.2, 0.2, 0.3, 0.2, 0.1]
else: # neutral oder None
tones = ["analytisch", "distanziert", "suggestiv", "überheblich", "provokativ"]
weights = [0.2, 0.2, 0.2, 0.2, 0.2]
# Intensität beeinflusst die Gewichtung
if self.intensity >= 4:
# Bei hoher Intensität mehr provokative und konfrontative Töne
weights = [w * (1 + (i % 3) * 0.2 * (self.intensity - 3)) for i, w in enumerate(weights)]
# Normalisieren der Gewichte
total = sum(weights)
weights = [w / total for w in weights]
return random.choices(tones, weights=weights, k=1)[0]
def _determine_focus(self, user_input: str) -> str:
"""Bestimmt den Fokus der Antwort basierend auf der Nutzereingabe"""
# Einfache Schlüsselwortanalyse (in einer vollständigen Implementierung
# würde hier eine komplexere NLP-Analyse stehen)
lower_input = user_input.lower()
if any(word in lower_input for word in ["mutter", "vater", "eltern", "familie", "kind"]):
return "familiäre Beziehungen"
elif any(word in lower_input for word in ["angst", "sorge", "furcht", "panik"]):
return "Ängste und Unsicherheiten"
elif any(word in lower_input for word in ["liebe", "beziehung", "partner", "ehe"]):
return "romantische Beziehungen"
elif any(word in lower_input for word in ["arbeit", "job", "karriere", "beruf"]):
return "berufliche Ambitionen"
elif any(word in lower_input for word in ["freund", "kollege", "bekannte"]):
return "soziale Beziehungen"
else:
return "persönliche Unsicherheiten"
def _determine_technique(self, emotion: Optional[str]) -> str:
"""Wählt eine psychoanalytische Technik basierend auf der Emotion"""
techniques = [
"Freie Assoziation",
"Traumdeutung",
"Übertragungsanalyse",
"Widerstandsanalyse",
"Projektion aufdecken",
"Verdrängung ansprechen",
"Abwehrmechanismen identifizieren"
]
# Bei negativen Emotionen eher konfrontative Techniken
if emotion == "negative":
return random.choice(techniques[3:])
# Bei positiven Emotionen eher subtile Techniken
elif emotion == "positive":
return random.choice(techniques[:4])
# Bei neutralen Emotionen zufällige Auswahl
else:
return random.choice(techniques)
def get_additional_context(self, strategy: Dict[str, any]) -> str:
"""
Generiert zusätzlichen Kontext für das LLM basierend auf der Strategie
Dies wird dem System-Prompt hinzugefügt, um die Antwortgenerierung zu steuern
"""
intensity_phrases = [
"Sei subtil in deiner Analyse.",
"Hinterfrage vorsichtig die Aussagen.",
"Sei direkter in deiner psychologischen Deutung.",
"Konfrontiere den Patienten mit seinen Widersprüchen.",
"Sei aggressiv in deiner Interpretation und Konfrontation."
]
intensity_instruction = intensity_phrases[min(self.intensity - 1, 4)]
context = (
f"Verwende einen {strategy['tone']} Ton. "
f"Fokussiere dich auf {strategy['focus']}. "
f"Nutze die Technik der {strategy['technique']}. "
f"{intensity_instruction}"
)
return context