Chat UI Redesign: 3-Spalten-Layout

Erstellt: 2025-12-27 | Aktualisiert: 2025-12-27

Task #424 - KORRIGIERTER Implementierungsplan
Version: 2.0 (nach kritischem Review)
Datum: 2025-12-27


Architektur-Entscheidungen

Wiederverwendung bestehender Infrastruktur

KomponenteStatusAktion
ManageConfigUseCaseExistiertWiederverwenden
ContentConfigRepositoryExistiertWiederverwenden
ConfigController (Web)ExistiertNicht ändern
Controller\Api\ConfigControllerFehltNEU erstellen

Korrigierte Prinzipien

PrinzipAlter PlanKorrektur
SRPChatController erweiternNeuer Api\ConfigController
DRYDoppelte DropdownsSettings-Bereich entfernen
MVCVersion-Logik im ControllerUseCase nutzen
ISPInterface unvollständigInterface erweitern
YAGNIHistory-BrowserNur Save = neue Version
WCAGFehlende ARIAVollständige A11y

Dateien und Änderungen

1. NEUER Controller: src/Controller/Api/ConfigController.php

<?php

declare(strict_types=1);

namespace Controller\Api;

// @responsibility: JSON-API für Config-Operationen (Chat-Integration)

use Framework\Controller;
use UseCases\Config\ManageConfigUseCase;

class ConfigController extends Controller
{
    public function __construct(
        private ManageConfigUseCase $configUseCase
    ) {
    }

    /**
     * GET /api/v1/config/{id}
     * Lädt Config mit Content für Anzeige
     */
    public function show(string $id): void
    {
        $config = $this->configUseCase->getById((int) $id);
        
        if ($config === null) {
            $this->json(['error' => 'Config nicht gefunden'], 404);
            return;
        }

        $this->json([
            'id' => $config->id,
            'name' => $config->name,
            'type' => $config->type,
            'content' => $config->content,
            'version' => $config->version,
        ]);
    }

    /**
     * POST /api/v1/config/{id}
     * Speichert neue Version (auto-increment)
     */
    public function update(string $id): void
    {
        $this->requireCsrf();

        $config = $this->configUseCase->getById((int) $id);
        if ($config === null) {
            $this->json(['error' => 'Config nicht gefunden'], 404);
            return;
        }

        $newContent = $_POST['content'] ?? '';
        
        // Auto-increment Version
        $currentVersion = $config->version ?? '1.0';
        $versionParts = explode('.', $currentVersion);
        $newVersion = $versionParts[0] . '.' . ((int) ($versionParts[1] ?? 0) + 1);

        $result = $this->configUseCase->update(
            id: (int) $id,
            name: $config->name,
            slug: $config->slug,
            description: $config->description,
            content: $newContent,
            newVersion: $newVersion,
            changeDescription: 'Chat UI Update',
            status: $config->status,
            parentId: $config->parentId
        );

        if (!$result->success) {
            $this->json(['error' => $result->message], 400);
            return;
        }

        $this->json([
            'success' => true,
            'version' => $newVersion,
            'message' => "Version {$newVersion} gespeichert",
        ]);
    }
}

Zeilen: ~70 | Dependencies: 1 (ManageConfigUseCase) | SRP: Nur Config-API


2. Routes: routes/api.php

Hinzufügen:

// Config API (für Chat-Integration)
use Controller\Api\ConfigController;

$router->get('/api/v1/config/{id}', [ConfigController::class, 'show']);
$router->post('/api/v1/config/{id}', [ConfigController::class, 'update']);

3. Interface erweitern: src/Domain/Repository/ContentConfigRepositoryInterface.php

interface ContentConfigRepositoryInterface
{
    // ... bestehende Methoden ...

    /**
     * Save version to history before update.
     */
    public function saveHistory(
        int $configId,
        string $content,
        string $version,
        string $changedBy,
        string $changeDescription
    ): void;

    /**
     * Get version history for a config.
     *
     * @return array<int, array<string, mixed>>
     */
    public function getHistory(int $configId, int $limit = 10): array;
}

4. View: src/View/chat/index.php

ENTFERNEN aus .chat-settings--advanced:

NEU einfügen nach <aside class="chat-sidebar">...</aside>:

<!-- Config Panel -->
<aside class="chat-config" id="configPanel">
    <div class="chat-config__header">
        <span>Konfiguration</span>
    </div>

    <!-- System Prompt -->
    <div class="chat-config__section" data-config-type="system_prompt">
        <label for="configSystemPrompt" class="chat-config__label">System Prompt</label>
        <div class="chat-config__row">
            <select name="system_prompt_id" id="configSystemPrompt" class="chat-config__select">
                <?php foreach ($systemPrompts ?? [] as $prompt): ?>
                <option value="<?= $prompt['id'] ?>"
                        data-content="<?= htmlspecialchars($prompt['content'] ?? '{}') ?>">
                    <?= htmlspecialchars($prompt['name']) ?>
                </option>
                <?php endforeach; ?>
            </select>
            <button type="button" 
                    class="chat-config__toggle"
                    aria-expanded="false"
                    aria-controls="systemPromptEdit"
                    aria-label="System Prompt bearbeiten">
                <span aria-hidden="true">▸</span>
            </button>
        </div>
        <div class="chat-config__edit" id="systemPromptEdit" hidden>
            <textarea id="systemPromptText" class="chat-config__textarea" rows="8"></textarea>
            <button type="button" class="chat-config__save" data-config-id="">
                Speichern
            </button>
        </div>
    </div>
    <!-- ... weitere Sections (Struktur, Autor-Profil) ... -->
</aside>

5. CSS: public/css/chat-redesign.css

/* CONFIG PANEL (3-Spalten-Layout) */

.chat-config {
    width: 300px;
    background: var(--chat-sidebar-bg);
    border-right: 1px solid var(--chat-border);
    display: flex;
    flex-direction: column;
    flex-shrink: 0;
    overflow-y: auto;
}

.chat-config__header {
    padding: 16px;
    font-size: 12px;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.5px;
    color: var(--chat-text-secondary);
    border-bottom: 1px solid var(--chat-border);
}

.chat-config__section { padding: 12px 16px; }
.chat-config__label { display: block; font-size: 11px; margin-bottom: 6px; }
.chat-config__row { display: flex; gap: 8px; align-items: center; }
.chat-config__select { flex: 1; padding: 8px 10px; border-radius: 6px; }
.chat-config__toggle { padding: 6px 10px; border-radius: 6px; cursor: pointer; }
.chat-config__textarea { width: 100%; font-family: monospace; font-size: 12px; }
.chat-config__save { width: 100%; padding: 8px; background: var(--chat-accent); }

@media (max-width: 1024px) {
    .chat-config { display: none; }
}

Zusammenfassung der Änderungen

DateiAktionZeilen
src/Controller/Api/ConfigController.phpNEU~70
routes/api.phpERWEITERN+3
src/Domain/Repository/ContentConfigRepositoryInterface.phpERWEITERN+15
src/View/chat/index.phpÄNDERN~100
public/css/chat-redesign.cssERWEITERN~120

Total neue Zeilen: ~310 | Geänderte Dateien: 5 | Neue Dateien: 1


Checkliste vor Implementation


Nicht implementiert (YAGNI)

Verwandte Themen