Backup #832
| ID | 832 |
| Dateipfad | /var/www/dev.campus.systemische-tools.de/src/UseCases/Chat/ManageChatSessionsUseCase.php |
| Version | 3 |
| Typ |
modified |
| Größe | 8.5 KB |
| Hash | 398e1de6b070bac424a801028857a1294cbfc50c4187bf3c13dca32e3b252df2 |
| Datum | 2025-12-23 08:16:02 |
| Geändert von | claude-code-hook |
| Grund | Claude Code Pre-Hook Backup vor Edit-Operation |
| Datei existiert |
Ja
|
Dateiinhalt
<?php
declare(strict_types=1);
namespace UseCases\Chat;
// @responsibility: Verwaltet Chat-Sessions (CRUD, Einstellungen, Collections)
use Infrastructure\AI\ModelConfig;
use Infrastructure\Persistence\ChatMessageRepository;
use Infrastructure\Persistence\ChatSessionRepository;
use Infrastructure\Persistence\CollectionRepository;
use Infrastructure\Persistence\ContentConfigRepository;
use Infrastructure\Validation\CollectionValidator;
final class ManageChatSessionsUseCase
{
private ChatSessionRepository $sessionRepo;
private ChatMessageRepository $messageRepo;
private ContentConfigRepository $configRepo;
private CollectionRepository $collectionRepo;
private CollectionValidator $collectionValidator;
private ?array $collectionsCache = null;
public function __construct(
?ChatSessionRepository $sessionRepo = null,
?ChatMessageRepository $messageRepo = null,
?ContentConfigRepository $configRepo = null,
?CollectionRepository $collectionRepo = null,
?CollectionValidator $collectionValidator = null
) {
$this->sessionRepo = $sessionRepo ?? new ChatSessionRepository();
$this->messageRepo = $messageRepo ?? new ChatMessageRepository();
$this->configRepo = $configRepo ?? new ContentConfigRepository();
$this->collectionRepo = $collectionRepo ?? new CollectionRepository();
$this->collectionValidator = $collectionValidator ?? new CollectionValidator($this->collectionRepo);
}
public function createSession(): string
{
$uuid = $this->sessionRepo->generateUuid();
$this->sessionRepo->create($uuid, 'claude-opus-4-5-20251101', '["documents"]', 5);
return $uuid;
}
public function getSession(string $uuid): ?array
{
return $this->sessionRepo->findByUuid($uuid);
}
public function getAllSessions(int $limit = 50): array
{
return $this->sessionRepo->findAll($limit);
}
public function getMessages(int $sessionId): array
{
return $this->messageRepo->findBySessionId($sessionId);
}
public function updateTitle(int $sessionId, string $title): string
{
$title = trim($title);
if ($title === '') {
$title = 'Neuer Chat';
}
$title = mb_substr($title, 0, 100);
$this->sessionRepo->updateTitle($sessionId, $title);
return $title;
}
public function updateSettings(
int $sessionId,
string $model,
array $collections,
int $contextLimit,
int $authorProfileId,
float $temperature,
int $maxTokens
): void {
$model = ModelConfig::validate($model);
$collections = $this->validateCollections($collections);
$contextLimit = $this->validateContextLimit($contextLimit);
$authorProfileId = $this->validateAuthorProfileId($authorProfileId);
$temperature = $this->validateTemperature($temperature);
$maxTokens = $this->validateMaxTokens($maxTokens);
$this->sessionRepo->updateSettings(
$sessionId,
$model,
$collections,
$contextLimit,
$authorProfileId > 0 ? $authorProfileId : null,
$temperature,
$maxTokens
);
}
public function updateSystemPrompt(int $sessionId, string $systemPrompt): ChatSessionResult
{
$maxLength = 2000;
$wasTruncated = mb_strlen($systemPrompt) > $maxLength;
$systemPrompt = trim(mb_substr($systemPrompt, 0, $maxLength));
$this->logSystemPromptChange($systemPrompt, $wasTruncated);
$this->sessionRepo->updateSystemPrompt($sessionId, $systemPrompt);
return ChatSessionResult::success('System-Prompt gespeichert.');
}
public function deleteSession(int $sessionId): void
{
$this->sessionRepo->delete($sessionId);
}
public function getAuthorProfiles(): array
{
return $this->configRepo->getAuthorProfiles();
}
public function getSystemPrompts(): array
{
return $this->configRepo->getSystemPrompts();
}
public function getOutputStructures(): array
{
return $this->configRepo->getStructures();
}
public function getStructure(int $id): ?array
{
return $this->configRepo->getStructure($id);
}
public function getAvailableCollections(): array
{
if ($this->collectionsCache === null) {
$this->collectionsCache = $this->collectionRepo->getSearchable();
if ($this->collectionsCache === []) {
$this->collectionsCache = [
['collection_id' => 'documents', 'display_name' => 'Dokumente', 'points_count' => 0, 'vector_size' => 1024],
];
}
}
return $this->collectionsCache;
}
public function validateCollectionCompatibility(array $collectionIds): array
{
if (empty($collectionIds)) {
return ['valid' => true, 'error' => null];
}
$result = $this->collectionValidator->validateSelection($collectionIds);
return [
'valid' => $result->isValid(),
'error' => $result->getError(),
];
}
public function getDefaultSystemPrompt(): string
{
return <<<'PROMPT'
Du bist ein hilfreicher Assistent für Fragen zu systemischem Teamcoaching und Teamentwicklung.
Beantworte die Frage des Nutzers basierend auf dem bereitgestellten Kontext.
- Antworte auf Deutsch
- Sei präzise und hilfreich
- Wenn der Kontext die Frage nicht beantwortet, sage das ehrlich
- Verweise auf die Quellen wenn passend
PROMPT;
}
public function settingsHaveChanged(array $session, string $model, array $collections, int $contextLimit, int $authorProfileId, float $temperature, int $maxTokens): bool
{
$currentModel = $session['model'] ?? '';
$currentCollections = $session['collections'] ?? '["documents"]';
$currentLimit = (int) ($session['context_limit'] ?? 5);
$currentProfileId = (int) ($session['author_profile_id'] ?? 0);
$currentTemperature = (float) ($session['temperature'] ?? 0.7);
$currentMaxTokens = (int) ($session['max_tokens'] ?? 4096);
$collectionsJson = json_encode($collections);
return $model !== $currentModel
|| $collectionsJson !== $currentCollections
|| $contextLimit !== $currentLimit
|| $authorProfileId !== $currentProfileId
|| $temperature !== $currentTemperature
|| $maxTokens !== $currentMaxTokens;
}
private function validateCollections(array|string $collections): array
{
$availableIds = array_column($this->getAvailableCollections(), 'collection_id');
if (is_string($collections)) {
$collections = [$collections];
}
$valid = array_filter($collections, fn ($c) => in_array($c, $availableIds, true));
return array_values($valid);
}
private function validateContextLimit(int $limit): int
{
$allowedLimits = [3, 5, 10, 15];
return in_array($limit, $allowedLimits, true) ? $limit : 5;
}
private function validateAuthorProfileId(int $profileId): int
{
if ($profileId === 0) {
return 0;
}
$profile = $this->configRepo->getAuthorProfile($profileId);
return $profile !== null ? $profileId : 0;
}
private function validateTemperature(float $temperature): float
{
return max(0.0, min(1.0, $temperature));
}
private function validateMaxTokens(int $maxTokens): int
{
$allowedValues = [1024, 2048, 4096, 8192];
return in_array($maxTokens, $allowedValues, true) ? $maxTokens : 4096;
}
private function logSystemPromptChange(string $prompt, bool $wasTruncated): void
{
$logData = [
'prompt_length' => mb_strlen($prompt),
'truncated' => $wasTruncated,
'ip' => $_SERVER['REMOTE_ADDR'] ?? 'unknown',
'timestamp' => date('c'),
];
try {
$devDb = \Infrastructure\Config\DatabaseFactory::dev();
$stmt = $devDb->prepare(
"INSERT INTO mcp_log (tool, operation, parameters, result, logged_at)
VALUES ('chat', 'system_prompt_change', :params, 'logged', NOW())"
);
$stmt->execute(['params' => json_encode($logData)]);
} catch (\Exception $e) {
// Silently fail
}
}
}
Vollständig herunterladen
Aktionen
Andere Versionen dieser Datei
| ID |
Version |
Typ |
Größe |
Datum |
| 1841 |
14 |
modified |
8.2 KB |
2025-12-27 23:21 |
| 1838 |
13 |
modified |
8.2 KB |
2025-12-27 23:20 |
| 1443 |
12 |
modified |
8.2 KB |
2025-12-25 17:00 |
| 1303 |
11 |
modified |
8.2 KB |
2025-12-25 13:29 |
| 1302 |
10 |
modified |
8.1 KB |
2025-12-25 13:29 |
| 1215 |
9 |
modified |
8.2 KB |
2025-12-25 10:41 |
| 1214 |
8 |
modified |
8.1 KB |
2025-12-25 10:40 |
| 1143 |
7 |
modified |
7.9 KB |
2025-12-25 09:45 |
| 1134 |
6 |
modified |
8.1 KB |
2025-12-25 09:41 |
| 1133 |
5 |
modified |
7.9 KB |
2025-12-25 09:41 |
| 1132 |
4 |
modified |
7.8 KB |
2025-12-25 09:41 |
| 832 |
3 |
modified |
8.5 KB |
2025-12-23 08:16 |
| 713 |
2 |
modified |
8.4 KB |
2025-12-23 07:55 |
| 545 |
1 |
modified |
8.1 KB |
2025-12-23 02:37 |
← Zurück zur Übersicht