<?php

/*
ET-Chat Copyright by SEDesign | ET-Chat v3.x.x Lizenz: CCPL | Autor: Evgeni Tcherkasski (info@s-e-d.de)
ET-Chat_T-FISH-MOD Weiterentwicklungen, Optimierungen und Ergänzungen am Code sind das geistige Eigentum von Tommy (Thomas Kuhn) und Harlekin (Bernd Witte).

Die darauf folgende Optimierungen und Ergänzungen am Code sind das Geistige Eigentum von Powermen (Christian K.) 
PHP 8/9 Ready, XML Parser, PDO Prepared Statements Get Set sicherheit usw.
*/

class AdminBadWords extends DbConectionMaker
{
    private $message = '';
    private $wordsFile = 'lang/bad_words.xml';
    
    public function __construct()
    {
        parent::__construct();

        if (session_id() == '') {
            session_start();
        }
		
        header('Cache-Control: no-store, no-cache, must-revalidate, pre-check=0, post-check=0, max-age=0');
        header('content-type: text/html; charset=utf-8');

        $langObj = new LangXml();
        $lang = $langObj->getLang()->admin[0];

        // Admin-Prüfung
        if ($_SESSION['etchat_' . $this->_prefix . 'user_priv'] != "admin") {
            echo "Zugriff verweigert.";
            return false;
        }
		
        // AJAX Request für GET (Wörter laden)
        if (isset($_SERVER['HTTP_X_REQUESTED_WITH']) && $_SERVER['HTTP_X_REQUESTED_WITH'] === 'XMLHttpRequest') {
            if ($_SERVER['REQUEST_METHOD'] === 'GET') {
                header('Content-Type: application/json');
                $words = $this->loadWords();
                echo json_encode(['words' => $words]);
                exit;
            }
        }
        
        // POST: Wort speichern (neu oder bearbeitet)
        if (isset($_POST['save_word'])) {
            $this->saveWord($_POST);
            exit;
        }
        
        // POST: Wort löschen
        if (isset($_POST['delete_word'])) {
            $this->deleteWord($_POST['delete_word']);
            exit;
        }
        
        // POST: Wort neu hinzufügen
        if (isset($_POST['add_word'])) {
            $this->addWord($_POST);
            exit;
        }

        $protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off') ? "https://" : "http://";
        $chat_url = $protocol . $_SERVER['HTTP_HOST'] . dirname($_SERVER['PHP_SELF']);
        $chat_url = rtrim($chat_url, '/\\') . '/';

        $this->initTemplate($lang, $chat_url);
    }
    
    private function loadWords()
    {
        $words = [];
        if (!file_exists($this->wordsFile)) {
            return $words;
        }
        
        $xml = simplexml_load_file($this->wordsFile);
        if (!$xml) {
            return $words;
        }
        
        foreach ($xml->word as $word) {
            $wordData = [
                'in' => (string)$word['in'],
                'out' => (string)$word['out'],
                'except' => []
            ];
            
            // Ausnahmen sammeln
            if ($word->except) {
                foreach ($word->except as $except) {
                    $wordData['except'][] = (string)$except;
                }
            }
            $words[] = $wordData;
        }
        
        return $words;
    }
    
    private function saveWord($postData)
    {
        $oldWord = $postData['old_word'] ?? '';
        $newWord = trim($postData['word_in'] ?? '');
        $newOut = trim($postData['word_out'] ?? '');
        $excepts = explode("\n", trim($postData['excepts'] ?? ''));
        $excepts = array_map('trim', $excepts);
        $excepts = array_filter($excepts);
        
        if (empty($newWord) || empty($newOut)) {
            echo json_encode(['success' => false, 'error' => 'Wort und Ersetzung sind Pflichtfelder']);
            return;
        }
        
        // DOMDocument für zuverlässige Bearbeitung
        $dom = new DOMDocument('1.0', 'UTF-8');
        $dom->preserveWhiteSpace = false;
        $dom->formatOutput = true;
        
        if (file_exists($this->wordsFile) && filesize($this->wordsFile) > 0) {
            $dom->load($this->wordsFile);
        } else {
            $root = $dom->createElement('content');
            $dom->appendChild($root);
        }
        
        $xpath = new DOMXPath($dom);
        
        // Altes Wort entfernen (wenn vorhanden und anders)
        if ($oldWord && $oldWord !== $newWord) {
            $oldNodes = $xpath->query("//word[@in='$oldWord']");
            foreach ($oldNodes as $oldNode) {
                $oldNode->parentNode->removeChild($oldNode);
            }
        }
        
        // Existiert das neue Wort bereits?
        $existingNodes = $xpath->query("//word[@in='$newWord']");
        
        if ($existingNodes->length > 0) {
            // Vorhandenes Wort aktualisieren
            $node = $existingNodes->item(0);
            $node->setAttribute('out', $newOut);
            
            // Alte excepts entfernen
            $oldExcept = $xpath->query("except", $node);
            foreach ($oldExcept as $except) {
                $except->parentNode->removeChild($except);
            }
            
            // Neue excepts hinzufügen
            foreach ($excepts as $except) {
                $exceptNode = $dom->createElement('except', htmlspecialchars($except));
                $node->appendChild($exceptNode);
            }
        } else {
            // Neues Wort erstellen
            $root = $dom->documentElement;
            $wordNode = $dom->createElement('word');
            $wordNode->setAttribute('in', $newWord);
            $wordNode->setAttribute('out', $newOut);
            
            foreach ($excepts as $except) {
                $exceptNode = $dom->createElement('except', htmlspecialchars($except));
                $wordNode->appendChild($exceptNode);
            }
            
            $root->appendChild($wordNode);
        }
        
        // XML speichern
        $dom->save($this->wordsFile);
        
        echo json_encode(['success' => true]);
    }
    
    private function deleteWord($wordIn)
    {
        if (empty($wordIn)) {
            echo json_encode(['success' => false, 'error' => 'Kein Wort zum Löschen']);
            return;
        }
        
        if (!file_exists($this->wordsFile)) {
            echo json_encode(['success' => false, 'error' => 'XML-Datei nicht gefunden']);
            return;
        }
        
        // DOMDocument für zuverlässiges Löschen
        $dom = new DOMDocument('1.0', 'UTF-8');
        $dom->preserveWhiteSpace = false;
        $dom->formatOutput = true;
        $dom->load($this->wordsFile);
        
        $xpath = new DOMXPath($dom);
        $nodes = $xpath->query("//word[@in='$wordIn']");
        
        if ($nodes->length === 0) {
            echo json_encode(['success' => false, 'error' => 'Wort nicht gefunden']);
            return;
        }
        
        // Knoten entfernen
        foreach ($nodes as $node) {
            $node->parentNode->removeChild($node);
        }
        
        // XML speichern
        $dom->save($this->wordsFile);
        
        echo json_encode(['success' => true]);
    }
    
    private function addWord($postData)
    {
        $this->saveWord($postData);
    }

    private function initTemplate($lang, $chat_url)
    {
        $message = $this->message;
        include_once("styles/admin_tpl/indexBadWords.tpl.html");
    }
}
?>