From 2f1025cd14513e3ffc16041631a4d447b94e4190 Mon Sep 17 00:00:00 2001 From: Till Tomczak Date: Mon, 16 Jun 2025 06:58:16 +0200 Subject: [PATCH] =?UTF-8?q?chore:=20=C3=84nderungen=20commited?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- backend/database/myp.db-shm | Bin 0 -> 32768 bytes backend/database/myp.db-wal | Bin 0 -> 28872 bytes backend/setup/modules/testing.sh | 823 +++++++++++++++++++++++++++++++ 3 files changed, 823 insertions(+) create mode 100644 backend/database/myp.db-shm create mode 100644 backend/database/myp.db-wal create mode 100644 backend/setup/modules/testing.sh diff --git a/backend/database/myp.db-shm b/backend/database/myp.db-shm new file mode 100644 index 0000000000000000000000000000000000000000..1d27e3425562cfc8073ea52a52a326ded0fd0049 GIT binary patch literal 32768 zcmeI)xd}o+5CG8ezQyn(Xb1LSW*~+}CKg~5X2#ltjTl;kU?aL;L`)P!41_l@%(BO@ zyaFaWk0Ot5%0fghulmTeYZd=%HFfV9BAP2UPEj$FBq-n$p*XO}fqY87}1Ev}qH!b?o#3 z0vYXL&&vu44v0laT=ow@LWt{X1qV*RiVJ8D@CU$!3wG4TcH2;8QMD=hTFRj_@%a1w zcskPWD|@26-}3=C_Ss^NY5D=5->TG`M}*u66-I3h- z%vxphihc7^n0sx=?j9QMbG@H*&rY$=*r9i+usVOWc5OqMttQtu^y}#j@mfktCoMH+ z7Pe_R8J*h6XtTv?$|_sRepy-ESf63cs%l11q3FmLct<#6p5HnNUysuC9QBy1TxXbz zzUbW3(_Fb%KY2?{t!lbGht77UGDKyQMs00{meX(UEWV-2+m=F0`Ke@Kf5})WDw|V# zmFd0R*?7hfE2+%p+WvwwMr1Fg;d_7|Go}fu*n)bSL)n4ribFVuS zc=$B4^|_^Kr~B28%qDja=1DCtU(KX4()wI_MO>)O?eN!g(>JOlF*%Vkmw9tSpUxz< zg~jyZUV2;LkAOAw)~6?Rre~Cwi7ZIoBs|_DH9bc@;j!DX*vJJwy8p%8$JXON2Asy8 z{<~aAAN*x7G4R#E%l&uz-2?##2!H?xfB*=900@8p2!O!{ zT++2h#T1AKn5-VFr9>enNxV#DMUC2_?k0+)))a|;MdDeCyb88n_cas|rrM#dCW^$? z6fwUdc9tTq+72j^h$`5jOHCB9))WbTMZ#H%ypSWHNF*||L!C_&39Tujens>wMS(Dh z#*Xe9t263oqKLMpi1-zeGZZOa+~Y9v;w@E@iSwTy$OZlyemJTv+*v{{&|YgI)PMj8 zfB*=900@8p2!O!36F@FNkPEm$3UYx{^QHfg3pA>5N~q}MOYNQujI6GXkKcN9AGyG} zue!JZ2!H?xfB*=900@8p2(%XgJM04^jyGKg{wqthvx-+iY`Ph@NnwuKOfLv z2ayZ3*AfjiAOHd&00JNY0w4eaAaL#kkP9Fec!FHOt9dC?q;`0Zz*9t!3%D?x4K$eC z%6kMq|Nhe_&wTskyT}F3ebvPUKmY_l00ck)1V8`;K%l({AQ!j*xqw&m(kOG@oqziK z3-}Zv7id)BYG8i>kI}_=k3j#M{rD*IUJr7C_FAH$1_VF=1V8`;KmY_l00hpR0CIs7 pxqw&C38Lau;ZJ|xK~E8Kfumm+aCU_V>^tZ&!t(+iqknr|;2&4?Q|JHy literal 0 HcmV?d00001 diff --git a/backend/setup/modules/testing.sh b/backend/setup/modules/testing.sh new file mode 100644 index 000000000..aa7a06f2a --- /dev/null +++ b/backend/setup/modules/testing.sh @@ -0,0 +1,823 @@ +#!/bin/bash + +####################################################################### +# MYP AIO-Installer - Testing & Validation Module +# +# Dieses Modul behandelt: +# - Python-Tests und Dependency-Validierung +# - Build-Prozess-Tests +# - Service-Start-Tests +# - Funktionalitäts-Tests +# - Performance-Tests +# - Integration-Tests +# - Upgrade-Funktionalität +####################################################################### + +# Funktionsdeklarationen für Testing & Validation + +test_installation() { + log "INFO" "=== INSTALLATIONS-TESTS DURCHFÜHREN ===" + + # System-Tests + test_system_health + + # Python-Environment-Tests + test_python_environment + + # Node.js-Environment-Tests + test_node_environment + + # Build-Prozess-Tests + test_build_process + + # Service-Tests + test_services + + # Netzwerk-Tests + test_networking + + # Security-Tests + test_security + + # Performance-Tests + test_performance + + # Integration-Tests + test_integration + + # Test-Report erstellen + create_test_report + + log "INFO" "Installations-Tests abgeschlossen" +} + +test_system_health() { + log "INFO" "=== SYSTEM-HEALTH-TESTS ===" + + local test_errors=0 + + # Betriebssystem-Check + log "INFO" "Teste Betriebssystem..." + if command -v lsb_release >/dev/null 2>&1; then + local os_info=$(lsb_release -d | cut -f2) + log "INFO" "Betriebssystem: $os_info" + else + log "WARN" "OS-Information nicht verfügbar" + test_errors=$((test_errors + 1)) + fi + + # Kernel-Check + log "INFO" "Teste Kernel..." + local kernel_version=$(uname -r) + log "INFO" "Kernel-Version: $kernel_version" + + # Speicher-Check + log "INFO" "Teste Speicher..." + local total_mem=$(free -m | awk 'NR==2{print $2}') + local free_mem=$(free -m | awk 'NR==2{print $7}') + log "INFO" "Gesamtspeicher: ${total_mem}MB, Verfügbar: ${free_mem}MB" + + if [[ $total_mem -lt 512 ]]; then + log "WARN" "Wenig Gesamtspeicher verfügbar ($total_mem MB)" + test_errors=$((test_errors + 1)) + fi + + if [[ $free_mem -lt 128 ]]; then + log "WARN" "Wenig freier Speicher verfügbar ($free_mem MB)" + test_errors=$((test_errors + 1)) + fi + + # Festplatten-Check + log "INFO" "Teste Festplattenspeicher..." + local disk_usage=$(df / | awk 'NR==2 {print $5}' | sed 's/%//') + local disk_free=$(df -h / | awk 'NR==2 {print $4}') + log "INFO" "Festplattenauslastung: $disk_usage%, Frei: $disk_free" + + if [[ $disk_usage -gt 90 ]]; then + log "ERROR" "Festplatte zu voll ($disk_usage%)" + test_errors=$((test_errors + 1)) + fi + + # CPU-Check + log "INFO" "Teste CPU..." + local cpu_count=$(nproc) + local load_avg=$(uptime | awk -F'load average:' '{print $2}' | awk '{print $1}' | sed 's/,//') + log "INFO" "CPU-Kerne: $cpu_count, Load Average: $load_avg" + + # Netzwerk-Interface-Check + log "INFO" "Teste Netzwerk-Interfaces..." + local interfaces=$(ip link show | grep "state UP" | wc -l) + log "INFO" "Aktive Netzwerk-Interfaces: $interfaces" + + if [[ $interfaces -eq 0 ]]; then + log "ERROR" "Keine aktiven Netzwerk-Interfaces" + test_errors=$((test_errors + 1)) + fi + + # Zeitzone-Check + log "INFO" "Teste Systemzeit..." + local current_time=$(date) + local timezone=$(timedatectl show --property=Timezone --value 2>/dev/null || echo "Unknown") + log "INFO" "Aktuelle Zeit: $current_time" + log "INFO" "Zeitzone: $timezone" + + if [[ $test_errors -eq 0 ]]; then + log "INFO" "✓ System-Health-Tests bestanden" + return 0 + else + log "ERROR" "✗ System-Health-Tests fehlgeschlagen ($test_errors Fehler)" + return 1 + fi +} + +test_python_environment() { + log "INFO" "=== PYTHON-ENVIRONMENT-TESTS ===" + + local test_errors=0 + + # Python-Version-Check + log "INFO" "Teste Python-Installation..." + if command -v python3 >/dev/null 2>&1; then + local python_version=$(python3 --version | cut -d' ' -f2) + log "INFO" "Python-Version: $python_version" + + # Version-Check (mindestens 3.8) + if ! python3 -c "import sys; sys.exit(0 if sys.version_info >= (3, 8) else 1)"; then + log "ERROR" "Python-Version zu alt (mindestens 3.8 erforderlich)" + test_errors=$((test_errors + 1)) + fi + else + log "ERROR" "Python3 nicht gefunden" + test_errors=$((test_errors + 1)) + fi + + # pip-Check + log "INFO" "Teste pip-Installation..." + if command -v pip3 >/dev/null 2>&1; then + local pip_version=$(pip3 --version | cut -d' ' -f2) + log "INFO" "pip-Version: $pip_version" + else + log "ERROR" "pip3 nicht gefunden" + test_errors=$((test_errors + 1)) + fi + + # Kritische Python-Packages testen + log "INFO" "Teste kritische Python-Packages..." + local critical_packages=( + "flask" + "flask_sqlalchemy" + "flask_login" + "flask_wtf" + "werkzeug" + "sqlalchemy" + "requests" + "cryptography" + "bcrypt" + ) + + for package in "${critical_packages[@]}"; do + if python3 -c "import $package" 2>/dev/null; then + local version=$(python3 -c "import $package; print(getattr($package, '__version__', 'unknown'))" 2>/dev/null) + log "INFO" "✓ $package ($version)" + else + log "ERROR" "✗ $package nicht verfügbar" + test_errors=$((test_errors + 1)) + fi + done + + # Python-Import-Test für MYP-Module + log "INFO" "Teste MYP-Python-Module..." + if [[ -f "$INSTALL_PATH/app.py" ]]; then + cd "$INSTALL_PATH" + + if python3 -c "import models" 2>/dev/null; then + log "INFO" "✓ models.py importiert" + else + log "ERROR" "✗ models.py Import fehlgeschlagen" + test_errors=$((test_errors + 1)) + fi + + # Flask-App-Import-Test + if python3 -c "from app import app" 2>/dev/null; then + log "INFO" "✓ Flask-App importiert" + else + log "ERROR" "✗ Flask-App Import fehlgeschlagen" + test_errors=$((test_errors + 1)) + fi + else + log "ERROR" "app.py nicht gefunden in $INSTALL_PATH" + test_errors=$((test_errors + 1)) + fi + + if [[ $test_errors -eq 0 ]]; then + log "INFO" "✓ Python-Environment-Tests bestanden" + return 0 + else + log "ERROR" "✗ Python-Environment-Tests fehlgeschlagen ($test_errors Fehler)" + return 1 + fi +} + +test_node_environment() { + log "INFO" "=== NODE.JS-ENVIRONMENT-TESTS ===" + + local test_errors=0 + + # Node.js-Check + log "INFO" "Teste Node.js-Installation..." + if command -v node >/dev/null 2>&1; then + local node_version=$(node --version) + log "INFO" "Node.js-Version: $node_version" + + # Version-Check (mindestens v16) + if ! node -e "process.exit(parseInt(process.version.slice(1)) >= 16 ? 0 : 1)"; then + log "WARN" "Node.js-Version könnte zu alt sein (empfohlen: v16+)" + fi + else + log "ERROR" "Node.js nicht gefunden" + test_errors=$((test_errors + 1)) + fi + + # npm-Check + log "INFO" "Teste npm-Installation..." + if command -v npm >/dev/null 2>&1; then + local npm_version=$(npm --version) + log "INFO" "npm-Version: $npm_version" + else + log "ERROR" "npm nicht gefunden" + test_errors=$((test_errors + 1)) + fi + + # Package.json-Check + if [[ -f "$INSTALL_PATH/package.json" ]]; then + log "INFO" "✓ package.json gefunden" + + cd "$INSTALL_PATH" + + # npm list Test + if npm list --depth=0 >/dev/null 2>&1; then + log "INFO" "✓ npm-Packages installiert" + else + log "WARN" "npm-Packages möglicherweise nicht vollständig installiert" + fi + + # TailwindCSS-Check + if npx tailwindcss --help >/dev/null 2>&1; then + log "INFO" "✓ TailwindCSS verfügbar" + else + log "WARN" "TailwindCSS nicht verfügbar" + fi + else + log "WARN" "package.json nicht gefunden" + fi + + if [[ $test_errors -eq 0 ]]; then + log "INFO" "✓ Node.js-Environment-Tests bestanden" + return 0 + else + log "ERROR" "✗ Node.js-Environment-Tests fehlgeschlagen ($test_errors Fehler)" + return 1 + fi +} + +test_build_process() { + log "INFO" "=== BUILD-PROZESS-TESTS ===" + + local test_errors=0 + + if [[ -f "$INSTALL_PATH/package.json" ]]; then + cd "$INSTALL_PATH" + + log "INFO" "Teste CSS-Build..." + if npm run build:css 2>/dev/null; then + log "INFO" "✓ CSS-Build erfolgreich" + + # Prüfe ob Output-Datei erstellt wurde + if [[ -f "static/css/output.css" ]]; then + log "INFO" "✓ CSS-Output-Datei erstellt" + else + log "ERROR" "✗ CSS-Output-Datei nicht erstellt" + test_errors=$((test_errors + 1)) + fi + else + log "ERROR" "✗ CSS-Build fehlgeschlagen" + test_errors=$((test_errors + 1)) + fi + else + log "WARN" "Kein package.json gefunden, überspringe Build-Tests" + fi + + # Asset-Komprimierung testen + log "INFO" "Teste Asset-Komprimierung..." + if [[ -f "$INSTALL_PATH/static/css/output.css.gz" ]]; then + log "INFO" "✓ CSS-Komprimierung funktioniert" + else + log "WARN" "CSS-Komprimierung nicht verfügbar" + fi + + if [[ $test_errors -eq 0 ]]; then + log "INFO" "✓ Build-Prozess-Tests bestanden" + return 0 + else + log "ERROR" "✗ Build-Prozess-Tests fehlgeschlagen ($test_errors Fehler)" + return 1 + fi +} + +test_services() { + log "INFO" "=== SERVICE-TESTS ===" + + local test_errors=0 + + # SystemD-Check + log "INFO" "Teste SystemD..." + if command -v systemctl >/dev/null 2>&1; then + log "INFO" "✓ SystemD verfügbar" + else + log "ERROR" "✗ SystemD nicht verfügbar" + test_errors=$((test_errors + 1)) + fi + + # Service-Dateien prüfen + local service_files=( + "/etc/systemd/system/${SERVICE_NAME}.service" + "/etc/systemd/system/${KIOSK_SERVICE}.service" + ) + + for service_file in "${service_files[@]}"; do + if [[ -f "$service_file" ]]; then + log "INFO" "✓ Service-Datei gefunden: $(basename "$service_file")" + else + log "ERROR" "✗ Service-Datei fehlt: $(basename "$service_file")" + test_errors=$((test_errors + 1)) + fi + done + + # Service-Status prüfen + log "INFO" "Teste Service-Status..." + + # Haupt-Service + if systemctl is-enabled --quiet "$SERVICE_NAME"; then + log "INFO" "✓ $SERVICE_NAME ist aktiviert" + else + log "ERROR" "✗ $SERVICE_NAME ist nicht aktiviert" + test_errors=$((test_errors + 1)) + fi + + # Service-Start-Test + log "INFO" "Teste Service-Start..." + if systemctl start "$SERVICE_NAME"; then + log "INFO" "✓ $SERVICE_NAME gestartet" + + # Warte auf Service-Start + sleep 5 + + if systemctl is-active --quiet "$SERVICE_NAME"; then + log "INFO" "✓ $SERVICE_NAME ist aktiv" + else + log "ERROR" "✗ $SERVICE_NAME ist nicht aktiv" + test_errors=$((test_errors + 1)) + fi + else + log "ERROR" "✗ $SERVICE_NAME konnte nicht gestartet werden" + test_errors=$((test_errors + 1)) + fi + + if [[ $test_errors -eq 0 ]]; then + log "INFO" "✓ Service-Tests bestanden" + return 0 + else + log "ERROR" "✗ Service-Tests fehlgeschlagen ($test_errors Fehler)" + return 1 + fi +} + +test_networking() { + log "INFO" "=== NETZWERK-TESTS ===" + + local test_errors=0 + + # HTTP-Service-Test + log "INFO" "Teste HTTP-Service..." + + # Warte auf Service + for i in {1..30}; do + if systemctl is-active --quiet "$SERVICE_NAME"; then + break + fi + sleep 2 + done + + # HTTP-Erreichbarkeit testen + local test_url="https://localhost" + log "INFO" "Teste URL: $test_url" + + if curl -f -s -k --connect-timeout 10 "$test_url" >/dev/null; then + log "INFO" "✓ HTTPS-Service erreichbar" + else + log "ERROR" "✗ HTTPS-Service nicht erreichbar" + test_errors=$((test_errors + 1)) + fi + + # Port-Check + log "INFO" "Teste offene Ports..." + local required_ports=("443" "80") + + for port in "${required_ports[@]}"; do + if ss -tlnp | grep ":$port " >/dev/null; then + log "INFO" "✓ Port $port ist offen" + else + log "ERROR" "✗ Port $port ist nicht offen" + test_errors=$((test_errors + 1)) + fi + done + + # DNS-Test + log "INFO" "Teste DNS-Auflösung..." + if nslookup google.com >/dev/null 2>&1; then + log "INFO" "✓ DNS-Auflösung funktioniert" + else + log "ERROR" "✗ DNS-Auflösung fehlgeschlagen" + test_errors=$((test_errors + 1)) + fi + + # Externe Konnektivität + log "INFO" "Teste externe Konnektivität..." + if ping -c 3 8.8.8.8 >/dev/null 2>&1; then + log "INFO" "✓ Externe Konnektivität funktioniert" + else + log "ERROR" "✗ Externe Konnektivität fehlgeschlagen" + test_errors=$((test_errors + 1)) + fi + + if [[ $test_errors -eq 0 ]]; then + log "INFO" "✓ Netzwerk-Tests bestanden" + return 0 + else + log "ERROR" "✗ Netzwerk-Tests fehlgeschlagen ($test_errors Fehler)" + return 1 + fi +} + +test_security() { + log "INFO" "=== SICHERHEITS-TESTS ===" + + local test_errors=0 + + # Firewall-Test + log "INFO" "Teste Firewall..." + if command -v ufw >/dev/null 2>&1; then + if ufw status | grep -q "Status: active"; then + log "INFO" "✓ UFW ist aktiv" + else + log "ERROR" "✗ UFW ist nicht aktiv" + test_errors=$((test_errors + 1)) + fi + else + log "ERROR" "✗ UFW nicht verfügbar" + test_errors=$((test_errors + 1)) + fi + + # SSH-Konfiguration testen + log "INFO" "Teste SSH-Konfiguration..." + if systemctl is-active --quiet ssh; then + log "INFO" "✓ SSH-Service aktiv" + + # SSH-Konfiguration prüfen + if grep -q "PermitRootLogin no" /etc/ssh/sshd_config*; then + log "INFO" "✓ Root-Login deaktiviert" + else + log "WARN" "Root-Login möglicherweise aktiviert" + fi + else + log "ERROR" "✗ SSH-Service nicht aktiv" + test_errors=$((test_errors + 1)) + fi + + # Fail2Ban-Test + log "INFO" "Teste Fail2Ban..." + if command -v fail2ban-server >/dev/null 2>&1; then + if systemctl is-active --quiet fail2ban; then + log "INFO" "✓ Fail2Ban aktiv" + else + log "WARN" "Fail2Ban nicht aktiv" + fi + else + log "WARN" "Fail2Ban nicht installiert" + fi + + # Benutzer-Berechtigungen testen + log "INFO" "Teste Benutzer-Berechtigungen..." + if id "$PROJECT_USER" &>/dev/null; then + log "INFO" "✓ MYP-Benutzer existiert" + + # Sudo-Rechte prüfen + if sudo -l -U "$PROJECT_USER" | grep -q "myp-"; then + log "INFO" "✓ MYP-Benutzer hat limitierte sudo-Rechte" + else + log "WARN" "MYP-Benutzer sudo-Rechte nicht konfiguriert" + fi + else + log "ERROR" "✗ MYP-Benutzer existiert nicht" + test_errors=$((test_errors + 1)) + fi + + # SSL-Zertifikat testen + log "INFO" "Teste SSL-Zertifikate..." + if [[ -f "$INSTALL_PATH/certs/myp.crt" ]] && [[ -f "$INSTALL_PATH/certs/myp.key" ]]; then + log "INFO" "✓ SSL-Zertifikate gefunden" + + # Zertifikat-Gültigkeit prüfen + if openssl x509 -in "$INSTALL_PATH/certs/myp.crt" -checkend 86400 >/dev/null; then + log "INFO" "✓ SSL-Zertifikat gültig" + else + log "WARN" "SSL-Zertifikat läuft bald ab" + fi + else + log "ERROR" "✗ SSL-Zertifikate nicht gefunden" + test_errors=$((test_errors + 1)) + fi + + if [[ $test_errors -eq 0 ]]; then + log "INFO" "✓ Sicherheits-Tests bestanden" + return 0 + else + log "ERROR" "✗ Sicherheits-Tests fehlgeschlagen ($test_errors Fehler)" + return 1 + fi +} + +test_performance() { + log "INFO" "=== PERFORMANCE-TESTS ===" + + local test_errors=0 + + # Service-Startup-Zeit messen + log "INFO" "Teste Service-Startup-Zeit..." + local start_time=$(date +%s) + systemctl restart "$SERVICE_NAME" + + # Warte auf Service-Start + for i in {1..60}; do + if systemctl is-active --quiet "$SERVICE_NAME"; then + local end_time=$(date +%s) + local startup_time=$((end_time - start_time)) + log "INFO" "✓ Service-Startup-Zeit: ${startup_time}s" + + if [[ $startup_time -gt 30 ]]; then + log "WARN" "Service-Startup-Zeit sehr lang (${startup_time}s)" + fi + break + fi + sleep 1 + done + + if ! systemctl is-active --quiet "$SERVICE_NAME"; then + log "ERROR" "✗ Service konnte nicht gestartet werden" + test_errors=$((test_errors + 1)) + fi + + # HTTP-Response-Zeit testen + log "INFO" "Teste HTTP-Response-Zeit..." + if systemctl is-active --quiet "$SERVICE_NAME"; then + # Warte zusätzlich für vollständigen Start + sleep 5 + + local response_time=$(curl -o /dev/null -s -w '%{time_total}' -k https://localhost 2>/dev/null || echo "999") + if [[ "$response_time" != "999" ]]; then + log "INFO" "✓ HTTP-Response-Zeit: ${response_time}s" + + if (( $(echo "$response_time > 5" | bc -l) )); then + log "WARN" "HTTP-Response-Zeit sehr lang (${response_time}s)" + fi + else + log "ERROR" "✗ HTTP-Response-Zeit nicht messbar" + test_errors=$((test_errors + 1)) + fi + fi + + # Speicherverbrauch testen + log "INFO" "Teste Speicherverbrauch..." + local mem_usage=$(ps aux | grep "[p]ython.*app.py" | awk '{sum+=$6} END {print sum/1024}' | cut -d. -f1) + if [[ -n "$mem_usage" && "$mem_usage" != "0" ]]; then + log "INFO" "✓ MYP-Service Speicherverbrauch: ${mem_usage}MB" + + if [[ $mem_usage -gt 256 ]]; then + log "WARN" "Hoher Speicherverbrauch (${mem_usage}MB)" + fi + else + log "WARN" "Speicherverbrauch nicht messbar" + fi + + if [[ $test_errors -eq 0 ]]; then + log "INFO" "✓ Performance-Tests bestanden" + return 0 + else + log "ERROR" "✗ Performance-Tests fehlgeschlagen ($test_errors Fehler)" + return 1 + fi +} + +test_integration() { + log "INFO" "=== INTEGRATION-TESTS ===" + + local test_errors=0 + + # Datei-Upload-Test + log "INFO" "Teste Datei-Upload-Verzeichnis..." + if [[ -d "$INSTALL_PATH/uploads" ]]; then + log "INFO" "✓ Upload-Verzeichnis existiert" + + # Schreibrechte testen + local test_file="$INSTALL_PATH/uploads/test-$(date +%s).txt" + if echo "test" > "$test_file" 2>/dev/null; then + log "INFO" "✓ Upload-Verzeichnis beschreibbar" + rm -f "$test_file" + else + log "ERROR" "✗ Upload-Verzeichnis nicht beschreibbar" + test_errors=$((test_errors + 1)) + fi + else + log "ERROR" "✗ Upload-Verzeichnis existiert nicht" + test_errors=$((test_errors + 1)) + fi + + # Datenbank-Test + log "INFO" "Teste Datenbank..." + if [[ -f "$INSTALL_PATH/database/myp.db" ]]; then + log "INFO" "✓ Datenbank-Datei existiert" + else + log "WARN" "Datenbank-Datei existiert noch nicht (wird beim ersten Start erstellt)" + fi + + # Logging-Test + log "INFO" "Teste Logging..." + if [[ -d "/var/log/myp" ]]; then + log "INFO" "✓ Log-Verzeichnis existiert" + + # Log-Schreibrechte testen + local test_log="/var/log/myp/test-$(date +%s).log" + if echo "test" > "$test_log" 2>/dev/null; then + log "INFO" "✓ Log-Verzeichnis beschreibbar" + rm -f "$test_log" + else + log "ERROR" "✗ Log-Verzeichnis nicht beschreibbar" + test_errors=$((test_errors + 1)) + fi + else + log "ERROR" "✗ Log-Verzeichnis existiert nicht" + test_errors=$((test_errors + 1)) + fi + + # Desktop-Integration testen + log "INFO" "Teste Desktop-Integration..." + if systemctl is-enabled --quiet lightdm 2>/dev/null; then + log "INFO" "✓ Display Manager konfiguriert" + else + log "WARN" "Display Manager nicht konfiguriert" + fi + + if systemctl is-enabled --quiet "$KIOSK_SERVICE" 2>/dev/null; then + log "INFO" "✓ Kiosk-Service aktiviert" + else + log "WARN" "Kiosk-Service nicht aktiviert" + fi + + if [[ $test_errors -eq 0 ]]; then + log "INFO" "✓ Integration-Tests bestanden" + return 0 + else + log "ERROR" "✗ Integration-Tests fehlgeschlagen ($test_errors Fehler)" + return 1 + fi +} + +create_test_report() { + log "INFO" "Erstelle Test-Report..." + + local report_file="/var/log/myp/installation-test-report-$(date +%Y%m%d-%H%M%S).txt" + local summary_file="/var/log/myp/test-summary.txt" + + cat > "$report_file" << EOF +================================================================================ +MYP INSTALLATIONS-TEST-REPORT +================================================================================ +Erstellt: $(date) +System: $(uname -a) +Hostname: $(hostname) +Installer-Version: 1.0.0 + +=== SYSTEM-INFORMATIONEN === +Betriebssystem: $(lsb_release -d 2>/dev/null | cut -f2 || echo "Unbekannt") +Kernel: $(uname -r) +Architektur: $(uname -m) +Gesamtspeicher: $(free -h | awk 'NR==2{print $2}') +Verfügbarer Speicher: $(free -h | awk 'NR==2{print $7}') +Festplattenspeicher: $(df -h / | awk 'NR==2{print $4}') verfügbar +CPU-Kerne: $(nproc) +Load Average: $(uptime | awk -F'load average:' '{print $2}' | awk '{print $1}' | sed 's/,//') + +=== PYTHON-UMGEBUNG === +Python-Version: $(python3 --version 2>/dev/null | cut -d' ' -f2 || echo "Nicht installiert") +pip-Version: $(pip3 --version 2>/dev/null | cut -d' ' -f2 || echo "Nicht installiert") +Installierte Packages: $(pip3 list 2>/dev/null | wc -l || echo "0") + +=== NODE.JS-UMGEBUNG === +Node.js-Version: $(node --version 2>/dev/null || echo "Nicht installiert") +npm-Version: $(npm --version 2>/dev/null || echo "Nicht installiert") + +=== SERVICES === +MYP-HTTPS-Service: $(systemctl is-active $SERVICE_NAME 2>/dev/null || echo "Nicht aktiv") +MYP-Kiosk-Service: $(systemctl is-active $KIOSK_SERVICE 2>/dev/null || echo "Nicht aktiv") +SSH-Service: $(systemctl is-active ssh 2>/dev/null || echo "Nicht aktiv") +Firewall: $(ufw status 2>/dev/null | head -1 | awk '{print $2}' || echo "Nicht verfügbar") + +=== NETZWERK === +Aktive Interfaces: $(ip link show | grep "state UP" | wc -l) +IP-Adressen: $(hostname -I) +DNS-Server: $(cat /etc/resolv.conf | grep nameserver | awk '{print $2}' | tr '\n' ' ') + +=== SICHERHEIT === +UFW-Status: $(ufw status 2>/dev/null | head -1 || echo "Nicht verfügbar") +Fail2Ban-Status: $(systemctl is-active fail2ban 2>/dev/null || echo "Nicht installiert") +SSH-Root-Login: $(grep -E "^PermitRootLogin" /etc/ssh/sshd_config* 2>/dev/null | head -1 | awk '{print $2}' || echo "Unbekannt") + +=== TEST-ERGEBNISSE === +EOF + + # Test-Ergebnisse anhängen + if test_system_health; then + echo "System Health: ✓ BESTANDEN" >> "$report_file" + else + echo "System Health: ✗ FEHLGESCHLAGEN" >> "$report_file" + fi + + if test_python_environment; then + echo "Python Environment: ✓ BESTANDEN" >> "$report_file" + else + echo "Python Environment: ✗ FEHLGESCHLAGEN" >> "$report_file" + fi + + if test_node_environment; then + echo "Node.js Environment: ✓ BESTANDEN" >> "$report_file" + else + echo "Node.js Environment: ✗ FEHLGESCHLAGEN" >> "$report_file" + fi + + if test_services; then + echo "Services: ✓ BESTANDEN" >> "$report_file" + else + echo "Services: ✗ FEHLGESCHLAGEN" >> "$report_file" + fi + + if test_networking; then + echo "Networking: ✓ BESTANDEN" >> "$report_file" + else + echo "Networking: ✗ FEHLGESCHLAGEN" >> "$report_file" + fi + + if test_security; then + echo "Security: ✓ BESTANDEN" >> "$report_file" + else + echo "Security: ✗ FEHLGESCHLAGEN" >> "$report_file" + fi + + cat >> "$report_file" << EOF + +=== EMPFEHLUNGEN === +1. Regelmäßige System-Updates durchführen +2. Firewall-Regeln regelmäßig überprüfen +3. SSL-Zertifikate vor Ablauf erneuern +4. Log-Dateien regelmäßig rotieren +5. Backup-Strategie implementieren + +=== NÄCHSTE SCHRITTE === +1. System neu starten: sudo reboot +2. MYP-System im Browser testen: https://$(hostname -I | awk '{print $1}') +3. Admin-Panel konfigurieren: https://$(hostname -I | awk '{print $1}')/admin +4. Benutzer und Drucker einrichten + +================================================================================ +ENDE REPORT +================================================================================ +EOF + + # Kurze Zusammenfassung erstellen + cat > "$summary_file" << EOF +MYP Installation Test Summary - $(date) +System Health: $(test_system_health && echo "✓" || echo "✗") +Python Environment: $(test_python_environment && echo "✓" || echo "✗") +Node.js Environment: $(test_node_environment && echo "✓" || echo "✗") +Services: $(test_services && echo "✓" || echo "✗") +Networking: $(test_networking && echo "✓" || echo "✗") +Security: $(test_security && echo "✓" || echo "✗") + +Report: $report_file +EOF + + log "INFO" "Test-Report erstellt: $report_file" + log "INFO" "Test-Zusammenfassung: $summary_file" + + # Report-Inhalte auch ins Log schreiben + cat "$summary_file" >> "$LOG_FILE" +} \ No newline at end of file