📚 Improved backend structure & error handling (#123) 🖥️🔧
This commit is contained in:
parent
8d29b2634a
commit
a36c14115a
@ -5611,10 +5611,10 @@ if __name__ == "__main__":
|
|||||||
threaded=True
|
threaded=True
|
||||||
)
|
)
|
||||||
else:
|
else:
|
||||||
app_logger.info("Starte HTTP-Server auf 0.0.0.0:8080")
|
app_logger.info("Starte HTTP-Server auf 0.0.0.0:80")
|
||||||
app.run(
|
app.run(
|
||||||
host="0.0.0.0",
|
host="0.0.0.0",
|
||||||
port=8080,
|
port=80,
|
||||||
debug=False,
|
debug=False,
|
||||||
threaded=True
|
threaded=True
|
||||||
)
|
)
|
||||||
|
@ -1,9 +1,10 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
|
|
||||||
# ===================================================================
|
# ===================================================================
|
||||||
# MYP Druckerverwaltung - Installer für Raspbian Kiosk-System
|
# MYP Druckerverwaltung - VOLLSTÄNDIGER KIOSK-INSTALLER für Raspbian
|
||||||
# Entwickelt auf Windows, ausführbar auf Raspberry Pi / Debian
|
# Entwickelt auf Windows, ausführbar auf Raspberry Pi / Debian
|
||||||
# OHNE virtualenv - verwendet System-Python mit --break-system-packages
|
# OHNE virtualenv - verwendet System-Python mit --break-system-packages
|
||||||
|
# ECHTER KIOSK-MODUS: Entfernt Desktop, 3 Backend-Instanzen, Autologin
|
||||||
# ===================================================================
|
# ===================================================================
|
||||||
|
|
||||||
set -euo pipefail
|
set -euo pipefail
|
||||||
@ -11,7 +12,10 @@ set -euo pipefail
|
|||||||
# =========================== KONFIGURATION ===========================
|
# =========================== KONFIGURATION ===========================
|
||||||
APP_NAME="MYP Druckerverwaltung"
|
APP_NAME="MYP Druckerverwaltung"
|
||||||
APP_DIR="/opt/myp"
|
APP_DIR="/opt/myp"
|
||||||
SERVICE_NAME="myp-kiosk"
|
SERVICE_NAME_KIOSK="myp-kiosk"
|
||||||
|
SERVICE_NAME_HTTPS="myp-https"
|
||||||
|
SERVICE_NAME_HTTP="myp-http"
|
||||||
|
KIOSK_USER="kiosk"
|
||||||
CURRENT_DIR="$(pwd)"
|
CURRENT_DIR="$(pwd)"
|
||||||
INSTALL_LOG="/var/log/myp-install.log"
|
INSTALL_LOG="/var/log/myp-install.log"
|
||||||
|
|
||||||
@ -60,6 +64,114 @@ check_debian_system() {
|
|||||||
log "✅ Debian/Raspbian-System erkannt"
|
log "✅ Debian/Raspbian-System erkannt"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# ========================== DESKTOP ENVIRONMENTS ENTFERNEN ==========================
|
||||||
|
remove_desktop_environments() {
|
||||||
|
log "=== ENTFERNE ALLE DESKTOP ENVIRONMENTS ==="
|
||||||
|
|
||||||
|
progress "Stoppe alle Desktop-Services..."
|
||||||
|
systemctl stop lightdm 2>/dev/null || true
|
||||||
|
systemctl stop gdm3 2>/dev/null || true
|
||||||
|
systemctl stop sddm 2>/dev/null || true
|
||||||
|
systemctl stop xdm 2>/dev/null || true
|
||||||
|
|
||||||
|
systemctl disable lightdm 2>/dev/null || true
|
||||||
|
systemctl disable gdm3 2>/dev/null || true
|
||||||
|
systemctl disable sddm 2>/dev/null || true
|
||||||
|
systemctl disable xdm 2>/dev/null || true
|
||||||
|
|
||||||
|
progress "Entferne Desktop-Pakete vollständig..."
|
||||||
|
|
||||||
|
# Raspberry Pi OS Desktop entfernen
|
||||||
|
apt-get remove --purge -y \
|
||||||
|
raspberrypi-ui-mods \
|
||||||
|
pi-package \
|
||||||
|
desktop-base \
|
||||||
|
lxde* \
|
||||||
|
xfce4* \
|
||||||
|
gnome* \
|
||||||
|
kde* \
|
||||||
|
mate* \
|
||||||
|
cinnamon* \
|
||||||
|
openbox \
|
||||||
|
pcmanfm \
|
||||||
|
file-manager* \
|
||||||
|
task-lxde-desktop \
|
||||||
|
task-xfce-desktop \
|
||||||
|
task-gnome-desktop \
|
||||||
|
task-kde-desktop \
|
||||||
|
2>/dev/null || true
|
||||||
|
|
||||||
|
# Display Manager entfernen
|
||||||
|
apt-get remove --purge -y \
|
||||||
|
lightdm* \
|
||||||
|
gdm3* \
|
||||||
|
sddm* \
|
||||||
|
xdm* \
|
||||||
|
nodm* \
|
||||||
|
2>/dev/null || true
|
||||||
|
|
||||||
|
# Unnötige Pakete entfernen
|
||||||
|
apt-get remove --purge -y \
|
||||||
|
libreoffice* \
|
||||||
|
thunderbird* \
|
||||||
|
firefox* \
|
||||||
|
chromium-browser \
|
||||||
|
vlc* \
|
||||||
|
gimp* \
|
||||||
|
scratch* \
|
||||||
|
minecraft-pi \
|
||||||
|
sonic-pi \
|
||||||
|
2>/dev/null || true
|
||||||
|
|
||||||
|
# Autoremove und Autoclean
|
||||||
|
apt-get autoremove --purge -y
|
||||||
|
apt-get autoclean
|
||||||
|
|
||||||
|
log "✅ Desktop Environments vollständig entfernt"
|
||||||
|
}
|
||||||
|
|
||||||
|
# ========================== KIOSK BENUTZER ERSTELLEN ==========================
|
||||||
|
create_kiosk_user() {
|
||||||
|
log "=== ERSTELLE KIOSK-BENUTZER ==="
|
||||||
|
|
||||||
|
# Kiosk-Benutzer erstellen falls nicht vorhanden
|
||||||
|
if ! id "$KIOSK_USER" &>/dev/null; then
|
||||||
|
progress "Erstelle Kiosk-Benutzer: $KIOSK_USER"
|
||||||
|
useradd -m -s /bin/bash "$KIOSK_USER" || error "Kann Kiosk-Benutzer nicht erstellen"
|
||||||
|
|
||||||
|
# Gruppen hinzufügen
|
||||||
|
usermod -aG audio,video,input,dialout,plugdev,users "$KIOSK_USER" 2>/dev/null || true
|
||||||
|
else
|
||||||
|
info "Kiosk-Benutzer $KIOSK_USER existiert bereits"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Passwort entfernen für automatischen Login
|
||||||
|
passwd -d "$KIOSK_USER" || warning "Konnte Passwort nicht entfernen"
|
||||||
|
|
||||||
|
log "✅ Kiosk-Benutzer erstellt: $KIOSK_USER"
|
||||||
|
}
|
||||||
|
|
||||||
|
# ========================== MINIMALE X11 INSTALLATION ==========================
|
||||||
|
install_minimal_x11() {
|
||||||
|
log "=== INSTALLIERE MINIMALE X11-UMGEBUNG ==="
|
||||||
|
|
||||||
|
progress "Installiere minimale X11-Pakete..."
|
||||||
|
apt-get install -y \
|
||||||
|
xserver-xorg-core \
|
||||||
|
xserver-xorg-input-all \
|
||||||
|
xserver-xorg-video-fbdev \
|
||||||
|
xserver-xorg-video-vesa \
|
||||||
|
xinit \
|
||||||
|
x11-xserver-utils \
|
||||||
|
xdotool \
|
||||||
|
unclutter \
|
||||||
|
chromium-browser \
|
||||||
|
openbox \
|
||||||
|
|| error "X11 Installation fehlgeschlagen"
|
||||||
|
|
||||||
|
log "✅ Minimale X11-Umgebung installiert"
|
||||||
|
}
|
||||||
|
|
||||||
# ========================== MERCEDES ZERTIFIKATE ==========================
|
# ========================== MERCEDES ZERTIFIKATE ==========================
|
||||||
install_mercedes_certificates() {
|
install_mercedes_certificates() {
|
||||||
log "=== INSTALLIERE MERCEDES SSL-ZERTIFIKATE ==="
|
log "=== INSTALLIERE MERCEDES SSL-ZERTIFIKATE ==="
|
||||||
@ -200,13 +312,287 @@ install_system_dependencies() {
|
|||||||
log "✅ Alle Abhängigkeiten erfolgreich installiert"
|
log "✅ Alle Abhängigkeiten erfolgreich installiert"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# ========================== 3 BACKEND SERVICES ERSTELLEN ==========================
|
||||||
|
create_backend_services() {
|
||||||
|
log "=== ERSTELLE 3 BACKEND-SERVICES ==="
|
||||||
|
|
||||||
|
# Service 1: Kiosk-Backend (Port 5000)
|
||||||
|
progress "Erstelle myp-kiosk.service (Port 5000)..."
|
||||||
|
cat > "/etc/systemd/system/${SERVICE_NAME_KIOSK}.service" << EOF
|
||||||
|
[Unit]
|
||||||
|
Description=MYP Kiosk Backend (Port 5000)
|
||||||
|
After=network.target network-online.target
|
||||||
|
Wants=network-online.target
|
||||||
|
Requires=network.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=simple
|
||||||
|
User=root
|
||||||
|
Group=root
|
||||||
|
WorkingDirectory=$APP_DIR
|
||||||
|
ExecStart=/usr/bin/python3 $APP_DIR/app.py --debug
|
||||||
|
Restart=always
|
||||||
|
RestartSec=5
|
||||||
|
StartLimitBurst=5
|
||||||
|
StartLimitInterval=60
|
||||||
|
|
||||||
|
# Umgebungsvariablen
|
||||||
|
Environment=PYTHONUNBUFFERED=1
|
||||||
|
Environment=FLASK_ENV=production
|
||||||
|
Environment=FLASK_HOST=0.0.0.0
|
||||||
|
Environment=FLASK_PORT=5000
|
||||||
|
Environment=PYTHONPATH=$APP_DIR
|
||||||
|
Environment=LC_ALL=C.UTF-8
|
||||||
|
Environment=LANG=C.UTF-8
|
||||||
|
|
||||||
|
# Logging
|
||||||
|
StandardOutput=journal
|
||||||
|
StandardError=journal
|
||||||
|
SyslogIdentifier=myp-kiosk
|
||||||
|
|
||||||
|
# Security-Einstellungen
|
||||||
|
NoNewPrivileges=true
|
||||||
|
PrivateTmp=false
|
||||||
|
ProtectSystem=strict
|
||||||
|
ReadWritePaths=$APP_DIR
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Service 2: HTTPS-Backend (Port 443)
|
||||||
|
progress "Erstelle myp-https.service (Port 443)..."
|
||||||
|
cat > "/etc/systemd/system/${SERVICE_NAME_HTTPS}.service" << EOF
|
||||||
|
[Unit]
|
||||||
|
Description=MYP HTTPS Backend (Port 443)
|
||||||
|
After=network.target network-online.target
|
||||||
|
Wants=network-online.target
|
||||||
|
Requires=network.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=simple
|
||||||
|
User=root
|
||||||
|
Group=root
|
||||||
|
WorkingDirectory=$APP_DIR
|
||||||
|
ExecStart=/usr/bin/python3 -c "
|
||||||
|
import sys, os
|
||||||
|
sys.path.insert(0, '$APP_DIR')
|
||||||
|
os.environ['FLASK_PORT'] = '443'
|
||||||
|
os.environ['FLASK_HOST'] = '0.0.0.0'
|
||||||
|
os.environ['FLASK_ENV'] = 'production'
|
||||||
|
from app import app, get_ssl_context
|
||||||
|
ssl_context = get_ssl_context()
|
||||||
|
if ssl_context:
|
||||||
|
app.run(host='0.0.0.0', port=443, debug=False, ssl_context=ssl_context, threaded=True)
|
||||||
|
else:
|
||||||
|
print('SSL-Kontext nicht verfügbar')
|
||||||
|
exit(1)
|
||||||
|
"
|
||||||
|
Restart=always
|
||||||
|
RestartSec=5
|
||||||
|
StartLimitBurst=5
|
||||||
|
StartLimitInterval=60
|
||||||
|
|
||||||
|
# Umgebungsvariablen
|
||||||
|
Environment=PYTHONUNBUFFERED=1
|
||||||
|
Environment=FLASK_ENV=production
|
||||||
|
Environment=FLASK_HOST=0.0.0.0
|
||||||
|
Environment=FLASK_PORT=443
|
||||||
|
Environment=PYTHONPATH=$APP_DIR
|
||||||
|
Environment=LC_ALL=C.UTF-8
|
||||||
|
Environment=LANG=C.UTF-8
|
||||||
|
|
||||||
|
# Logging
|
||||||
|
StandardOutput=journal
|
||||||
|
StandardError=journal
|
||||||
|
SyslogIdentifier=myp-https
|
||||||
|
|
||||||
|
# Security-Einstellungen
|
||||||
|
NoNewPrivileges=true
|
||||||
|
PrivateTmp=false
|
||||||
|
ProtectSystem=strict
|
||||||
|
ReadWritePaths=$APP_DIR
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Service 3: HTTP-Backend (Port 80)
|
||||||
|
progress "Erstelle myp-http.service (Port 80)..."
|
||||||
|
cat > "/etc/systemd/system/${SERVICE_NAME_HTTP}.service" << EOF
|
||||||
|
[Unit]
|
||||||
|
Description=MYP HTTP Backend (Port 80)
|
||||||
|
After=network.target network-online.target
|
||||||
|
Wants=network-online.target
|
||||||
|
Requires=network.target
|
||||||
|
|
||||||
|
[Service]
|
||||||
|
Type=simple
|
||||||
|
User=root
|
||||||
|
Group=root
|
||||||
|
WorkingDirectory=$APP_DIR
|
||||||
|
ExecStart=/usr/bin/python3 -c "
|
||||||
|
import sys, os
|
||||||
|
sys.path.insert(0, '$APP_DIR')
|
||||||
|
os.environ['FLASK_PORT'] = '80'
|
||||||
|
os.environ['FLASK_HOST'] = '0.0.0.0'
|
||||||
|
os.environ['FLASK_ENV'] = 'production'
|
||||||
|
from app import app
|
||||||
|
app.run(host='0.0.0.0', port=80, debug=False, threaded=True)
|
||||||
|
"
|
||||||
|
Restart=always
|
||||||
|
RestartSec=5
|
||||||
|
StartLimitBurst=5
|
||||||
|
StartLimitInterval=60
|
||||||
|
|
||||||
|
# Umgebungsvariablen
|
||||||
|
Environment=PYTHONUNBUFFERED=1
|
||||||
|
Environment=FLASK_ENV=production
|
||||||
|
Environment=FLASK_HOST=0.0.0.0
|
||||||
|
Environment=FLASK_PORT=80
|
||||||
|
Environment=PYTHONPATH=$APP_DIR
|
||||||
|
Environment=LC_ALL=C.UTF-8
|
||||||
|
Environment=LANG=C.UTF-8
|
||||||
|
|
||||||
|
# Logging
|
||||||
|
StandardOutput=journal
|
||||||
|
StandardError=journal
|
||||||
|
SyslogIdentifier=myp-http
|
||||||
|
|
||||||
|
# Security-Einstellungen
|
||||||
|
NoNewPrivileges=true
|
||||||
|
PrivateTmp=false
|
||||||
|
ProtectSystem=strict
|
||||||
|
ReadWritePaths=$APP_DIR
|
||||||
|
|
||||||
|
[Install]
|
||||||
|
WantedBy=multi-user.target
|
||||||
|
EOF
|
||||||
|
|
||||||
|
log "✅ 3 Backend-Services erstellt"
|
||||||
|
}
|
||||||
|
|
||||||
|
# ========================== AUTOLOGIN KONFIGURIEREN ==========================
|
||||||
|
configure_autologin() {
|
||||||
|
log "=== KONFIGURIERE AUTOLOGIN ==="
|
||||||
|
|
||||||
|
progress "Erstelle Autologin-Service..."
|
||||||
|
|
||||||
|
# Getty-Service für automatischen Login überschreiben
|
||||||
|
mkdir -p /etc/systemd/system/getty@tty1.service.d/
|
||||||
|
cat > /etc/systemd/system/getty@tty1.service.d/autologin.conf << EOF
|
||||||
|
[Service]
|
||||||
|
ExecStart=
|
||||||
|
ExecStart=-/sbin/agetty --autologin $KIOSK_USER --noclear %I linux
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Systemd Target auf Multi-User setzen (ohne grafisches Login)
|
||||||
|
systemctl set-default multi-user.target
|
||||||
|
|
||||||
|
log "✅ Autologin konfiguriert für Benutzer: $KIOSK_USER"
|
||||||
|
}
|
||||||
|
|
||||||
|
# ========================== KIOSK BROWSER KONFIGURATION ==========================
|
||||||
|
configure_kiosk_browser() {
|
||||||
|
log "=== KONFIGURIERE KIOSK-BROWSER ==="
|
||||||
|
|
||||||
|
KIOSK_HOME="/home/$KIOSK_USER"
|
||||||
|
|
||||||
|
# .bashrc für automatischen X-Start erweitern
|
||||||
|
progress "Konfiguriere automatischen X-Start..."
|
||||||
|
cat >> "$KIOSK_HOME/.bashrc" << 'EOF'
|
||||||
|
|
||||||
|
# Automatischer X-Start für Kiosk-Modus
|
||||||
|
if [ -z "$DISPLAY" ] && [ "$(tty)" = "/dev/tty1" ]; then
|
||||||
|
exec startx
|
||||||
|
fi
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# .xinitrc für Kiosk-Session erstellen
|
||||||
|
progress "Erstelle Kiosk X-Session..."
|
||||||
|
cat > "$KIOSK_HOME/.xinitrc" << 'EOF'
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# Bildschirmschoner und Energieverwaltung deaktivieren
|
||||||
|
xset s off
|
||||||
|
xset s noblank
|
||||||
|
xset s noexpose
|
||||||
|
xset -dpms
|
||||||
|
|
||||||
|
# Mauszeiger verstecken
|
||||||
|
unclutter -idle 0.5 -root &
|
||||||
|
|
||||||
|
# Warte auf Backend-Services
|
||||||
|
echo "Warte auf MYP Backend-Services..."
|
||||||
|
WAIT_COUNT=0
|
||||||
|
while ! curl -s http://localhost:5000 > /dev/null; do
|
||||||
|
echo "Warte auf Backend (Port 5000)... ($WAIT_COUNT/60)"
|
||||||
|
sleep 2
|
||||||
|
WAIT_COUNT=$((WAIT_COUNT + 1))
|
||||||
|
if [ $WAIT_COUNT -gt 60 ]; then
|
||||||
|
echo "FEHLER: Backend nach 120s nicht erreichbar!"
|
||||||
|
break
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
|
echo "Backend erreichbar - starte Kiosk-Browser..."
|
||||||
|
|
||||||
|
# Chromium im Vollbild-Kiosk-Modus
|
||||||
|
exec chromium-browser \
|
||||||
|
--kiosk \
|
||||||
|
--no-sandbox \
|
||||||
|
--disable-infobars \
|
||||||
|
--disable-session-crashed-bubble \
|
||||||
|
--disable-restore-session-state \
|
||||||
|
--disable-web-security \
|
||||||
|
--disable-features=TranslateUI \
|
||||||
|
--disable-extensions \
|
||||||
|
--disable-plugins \
|
||||||
|
--disable-popup-blocking \
|
||||||
|
--disable-prompt-on-repost \
|
||||||
|
--disable-sync \
|
||||||
|
--disable-translate \
|
||||||
|
--noerrdialogs \
|
||||||
|
--no-first-run \
|
||||||
|
--no-default-browser-check \
|
||||||
|
--autoplay-policy=no-user-gesture-required \
|
||||||
|
--start-fullscreen \
|
||||||
|
--window-position=0,0 \
|
||||||
|
--user-data-dir=/home/kiosk/.chromium-kiosk \
|
||||||
|
--disable-background-mode \
|
||||||
|
--force-device-scale-factor=1.0 \
|
||||||
|
--disable-pinch \
|
||||||
|
--overscroll-history-navigation=0 \
|
||||||
|
--disable-dev-shm-usage \
|
||||||
|
--memory-pressure-off \
|
||||||
|
--max_old_space_size=512 \
|
||||||
|
http://localhost:5000
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Berechtigungen setzen
|
||||||
|
chmod +x "$KIOSK_HOME/.xinitrc"
|
||||||
|
chown -R "$KIOSK_USER:$KIOSK_USER" "$KIOSK_HOME"
|
||||||
|
|
||||||
|
log "✅ Kiosk-Browser konfiguriert"
|
||||||
|
}
|
||||||
|
|
||||||
# ========================== PRODUKTIONS-KIOSK SETUP ==========================
|
# ========================== PRODUKTIONS-KIOSK SETUP ==========================
|
||||||
setup_production_kiosk() {
|
setup_production_kiosk() {
|
||||||
log "=== RICHTE PRODUKTIONS-KIOSK-MODUS EIN ==="
|
log "=== RICHTE PRODUKTIONS-KIOSK-MODUS EIN ==="
|
||||||
|
|
||||||
# Zuerst Abhängigkeiten installieren
|
# 1. System-Abhängigkeiten installieren
|
||||||
install_system_dependencies
|
install_system_dependencies
|
||||||
|
|
||||||
|
# 2. Desktop-Environments entfernen
|
||||||
|
remove_desktop_environments
|
||||||
|
|
||||||
|
# 3. Minimale X11-Umgebung installieren
|
||||||
|
install_minimal_x11
|
||||||
|
|
||||||
|
# 4. Kiosk-Benutzer erstellen
|
||||||
|
create_kiosk_user
|
||||||
|
|
||||||
|
# 5. Anwendung kopieren
|
||||||
progress "Erstelle Zielverzeichnis /opt/myp..."
|
progress "Erstelle Zielverzeichnis /opt/myp..."
|
||||||
mkdir -p "$APP_DIR" || error "Konnte Zielverzeichnis nicht erstellen"
|
mkdir -p "$APP_DIR" || error "Konnte Zielverzeichnis nicht erstellen"
|
||||||
|
|
||||||
@ -263,114 +649,113 @@ setup_production_kiosk() {
|
|||||||
chmod 750 "$APP_DIR/logs"
|
chmod 750 "$APP_DIR/logs"
|
||||||
chmod 755 "$APP_DIR/uploads"
|
chmod 755 "$APP_DIR/uploads"
|
||||||
|
|
||||||
progress "Erstelle Systemd-Service myp-kiosk.service..."
|
# 6. Backend-Services erstellen
|
||||||
cat > "/etc/systemd/system/${SERVICE_NAME}.service" << EOF
|
create_backend_services
|
||||||
[Unit]
|
|
||||||
Description=MYP Druckerverwaltung Kiosk-Modus
|
|
||||||
After=network.target network-online.target
|
|
||||||
Wants=network-online.target
|
|
||||||
Requires=network.target
|
|
||||||
|
|
||||||
[Service]
|
|
||||||
Type=simple
|
|
||||||
User=root
|
|
||||||
Group=root
|
|
||||||
WorkingDirectory=$APP_DIR
|
|
||||||
ExecStart=/usr/bin/python3 $APP_DIR/app.py --debug
|
|
||||||
Restart=always
|
|
||||||
RestartSec=5
|
|
||||||
StartLimitBurst=5
|
|
||||||
StartLimitInterval=60
|
|
||||||
|
|
||||||
# Umgebungsvariablen
|
|
||||||
Environment=PYTHONUNBUFFERED=1
|
|
||||||
Environment=FLASK_ENV=production
|
|
||||||
Environment=FLASK_HOST=0.0.0.0
|
|
||||||
Environment=FLASK_PORT=5000
|
|
||||||
Environment=PYTHONPATH=$APP_DIR
|
|
||||||
Environment=LC_ALL=C.UTF-8
|
|
||||||
Environment=LANG=C.UTF-8
|
|
||||||
|
|
||||||
# Logging
|
|
||||||
StandardOutput=journal
|
|
||||||
StandardError=journal
|
|
||||||
SyslogIdentifier=myp-kiosk
|
|
||||||
|
|
||||||
# Security-Einstellungen
|
|
||||||
NoNewPrivileges=true
|
|
||||||
PrivateTmp=false
|
|
||||||
ProtectSystem=strict
|
|
||||||
ReadWritePaths=$APP_DIR
|
|
||||||
|
|
||||||
[Install]
|
|
||||||
WantedBy=multi-user.target
|
|
||||||
EOF
|
|
||||||
|
|
||||||
|
# 7. Autologin konfigurieren
|
||||||
|
configure_autologin
|
||||||
|
|
||||||
|
# 8. Kiosk-Browser konfigurieren
|
||||||
|
configure_kiosk_browser
|
||||||
|
|
||||||
|
# 9. Services aktivieren und starten
|
||||||
progress "Lade Systemd-Konfiguration neu..."
|
progress "Lade Systemd-Konfiguration neu..."
|
||||||
systemctl daemon-reload || error "Systemd Reload fehlgeschlagen"
|
systemctl daemon-reload || error "Systemd Reload fehlgeschlagen"
|
||||||
|
|
||||||
progress "Aktiviere und starte $SERVICE_NAME Service..."
|
progress "Aktiviere alle Backend-Services..."
|
||||||
systemctl enable "$SERVICE_NAME.service" || error "Service Enable fehlgeschlagen"
|
systemctl enable "$SERVICE_NAME_KIOSK.service" || error "Kiosk-Service Enable fehlgeschlagen"
|
||||||
systemctl start "$SERVICE_NAME.service" || error "Service Start fehlgeschlagen"
|
systemctl enable "$SERVICE_NAME_HTTPS.service" || error "HTTPS-Service Enable fehlgeschlagen"
|
||||||
|
systemctl enable "$SERVICE_NAME_HTTP.service" || error "HTTP-Service Enable fehlgeschlagen"
|
||||||
|
|
||||||
|
progress "Starte alle Backend-Services..."
|
||||||
|
systemctl start "$SERVICE_NAME_KIOSK.service" || error "Kiosk-Service Start fehlgeschlagen"
|
||||||
|
systemctl start "$SERVICE_NAME_HTTPS.service" || warning "HTTPS-Service Start fehlgeschlagen (SSL möglicherweise nicht konfiguriert)"
|
||||||
|
systemctl start "$SERVICE_NAME_HTTP.service" || error "HTTP-Service Start fehlgeschlagen"
|
||||||
|
|
||||||
# Service-Status prüfen
|
# Service-Status prüfen
|
||||||
sleep 5
|
sleep 5
|
||||||
if systemctl is-active --quiet "$SERVICE_NAME.service"; then
|
|
||||||
log "✅ $SERVICE_NAME Service läuft erfolgreich"
|
info "=== SERVICE-STATUS ==="
|
||||||
info "Service-Status: $(systemctl is-active $SERVICE_NAME.service)"
|
for service in "$SERVICE_NAME_KIOSK" "$SERVICE_NAME_HTTPS" "$SERVICE_NAME_HTTP"; do
|
||||||
info "Port 5000: Flask-App läuft im Debug-Modus"
|
if systemctl is-active --quiet "$service.service"; then
|
||||||
info "Projektverzeichnis: $APP_DIR"
|
log "✅ $service Service läuft erfolgreich"
|
||||||
|
|
||||||
# Test der Anwendung
|
|
||||||
progress "Teste Anwendungserreichbarkeit..."
|
|
||||||
sleep 3
|
|
||||||
if curl -s http://localhost:5000 > /dev/null 2>&1; then
|
|
||||||
log "✅ Anwendung ist unter http://localhost:5000 erreichbar"
|
|
||||||
else
|
else
|
||||||
warning "⚠️ Anwendung noch nicht erreichbar (möglicherweise noch beim Starten)"
|
warning "⚠️ $service Service läuft nicht - prüfen Sie die Logs: journalctl -u $service -f"
|
||||||
fi
|
fi
|
||||||
|
done
|
||||||
|
|
||||||
|
# Backend-Tests
|
||||||
|
progress "Teste Backend-Erreichbarkeit..."
|
||||||
|
sleep 3
|
||||||
|
|
||||||
|
if curl -s http://localhost:5000 > /dev/null 2>&1; then
|
||||||
|
log "✅ Port 5000 (Kiosk) erreichbar"
|
||||||
else
|
else
|
||||||
error "$SERVICE_NAME Service konnte nicht gestartet werden - prüfen Sie die Logs: journalctl -u $SERVICE_NAME -f"
|
warning "⚠️ Port 5000 (Kiosk) nicht erreichbar"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
log "✅ Produktions-Kiosk-Modus erfolgreich eingerichtet"
|
if curl -s http://localhost:80 > /dev/null 2>&1; then
|
||||||
log "🎯 Anwendung erreichbar unter: http://localhost:5000"
|
log "✅ Port 80 (HTTP) erreichbar"
|
||||||
log "📋 Service-Befehle:"
|
else
|
||||||
log " • Status: sudo systemctl status $SERVICE_NAME"
|
warning "⚠️ Port 80 (HTTP) nicht erreichbar"
|
||||||
log " • Stoppen: sudo systemctl stop $SERVICE_NAME"
|
fi
|
||||||
log " • Starten: sudo systemctl start $SERVICE_NAME"
|
|
||||||
log " • Neustarten: sudo systemctl restart $SERVICE_NAME"
|
if curl -k -s https://localhost:443 > /dev/null 2>&1; then
|
||||||
log " • Logs: sudo journalctl -u $SERVICE_NAME -f"
|
log "✅ Port 443 (HTTPS) erreichbar"
|
||||||
log " • Service-Info: sudo journalctl -u $SERVICE_NAME --no-pager"
|
else
|
||||||
|
warning "⚠️ Port 443 (HTTPS) nicht erreichbar (SSL möglicherweise nicht konfiguriert)"
|
||||||
|
fi
|
||||||
|
|
||||||
|
log "✅ PRODUKTIONS-KIOSK-MODUS ERFOLGREICH EINGERICHTET"
|
||||||
|
log ""
|
||||||
|
log "🚀 WICHTIG: NEUSTART ERFORDERLICH!"
|
||||||
|
log " sudo reboot"
|
||||||
|
log ""
|
||||||
|
log "📊 NACH DEM NEUSTART:"
|
||||||
|
log " • Automatischer Login als Benutzer: $KIOSK_USER"
|
||||||
|
log " • Automatischer X-Start und Chromium-Kiosk"
|
||||||
|
log " • Backend läuft auf 3 Ports:"
|
||||||
|
log " - http://localhost:5000 (Kiosk-Anzeige)"
|
||||||
|
log " - http://localhost:80 (HTTP-API)"
|
||||||
|
log " - https://localhost:443 (HTTPS-API)"
|
||||||
|
log ""
|
||||||
|
log "🔧 SERVICE-BEFEHLE:"
|
||||||
|
log " • Status: sudo systemctl status myp-{kiosk,https,http}"
|
||||||
|
log " • Logs: sudo journalctl -u myp-kiosk -f"
|
||||||
|
log " • Restart: sudo systemctl restart myp-{kiosk,https,http}"
|
||||||
|
log ""
|
||||||
|
warning "🔄 FÜHRE JETZT 'sudo reboot' AUS, UM DEN KIOSK-MODUS ZU AKTIVIEREN!"
|
||||||
}
|
}
|
||||||
|
|
||||||
# ========================== HAUPTMENÜ ==========================
|
# ========================== HAUPTMENÜ ==========================
|
||||||
show_menu() {
|
show_menu() {
|
||||||
clear
|
clear
|
||||||
echo -e "${BLUE}=================================================================${NC}"
|
echo -e "${BLUE}=================================================================${NC}"
|
||||||
echo -e "${GREEN} $APP_NAME - Installer für Raspbian${NC}"
|
echo -e "${GREEN} $APP_NAME - VOLLSTÄNDIGER KIOSK-INSTALLER${NC}"
|
||||||
echo -e "${BLUE}=================================================================${NC}"
|
echo -e "${BLUE}=================================================================${NC}"
|
||||||
echo ""
|
echo ""
|
||||||
echo -e "${YELLOW}Aktuelles Verzeichnis:${NC} $CURRENT_DIR"
|
echo -e "${YELLOW}Aktuelles Verzeichnis:${NC} $CURRENT_DIR"
|
||||||
echo -e "${YELLOW}Systemzeit:${NC} $(date)"
|
echo -e "${YELLOW}Systemzeit:${NC} $(date)"
|
||||||
echo -e "${YELLOW}Zielverzeichnis:${NC} $APP_DIR"
|
echo -e "${YELLOW}Zielverzeichnis:${NC} $APP_DIR"
|
||||||
|
echo -e "${YELLOW}Kiosk-Benutzer:${NC} $KIOSK_USER"
|
||||||
echo ""
|
echo ""
|
||||||
echo -e "${PURPLE}Wählen Sie eine Option:${NC}"
|
echo -e "${PURPLE}Wählen Sie eine Option:${NC}"
|
||||||
echo ""
|
echo ""
|
||||||
echo -e "${GREEN}1)${NC} System vorbereiten (Abhängigkeiten installieren)"
|
echo -e "${GREEN}1)${NC} System vorbereiten (Abhängigkeiten installieren)"
|
||||||
echo -e " → Installiert Python 3, pip und alle benötigten Pakete"
|
echo -e " → Installiert Python 3, pip und alle benötigten Pakete"
|
||||||
echo -e " → Verwendet: pip install --break-system-packages"
|
echo -e " → Verwendet: pip install --break-system-packages"
|
||||||
echo -e " → Keine virtualenv, direktes System-Python"
|
echo -e " → Mercedes SSL-Zertifikate werden konfiguriert"
|
||||||
echo ""
|
echo ""
|
||||||
echo -e "${GREEN}2)${NC} Produktions-Kiosk-Modus installieren"
|
echo -e "${GREEN}2)${NC} VOLLSTÄNDIGER KIOSK-MODUS installieren"
|
||||||
echo -e " → Führt System-Vorbereitung durch"
|
echo -e " → ${RED}ENTFERNT ALLE DESKTOP-ENVIRONMENTS!${NC}"
|
||||||
echo -e " → Verschiebt Dateien selektiv nach /opt/myp/"
|
echo -e " → Installiert minimale X11-Umgebung"
|
||||||
echo -e " → Erstellt systemd-Service: myp-kiosk.service"
|
echo -e " → Erstellt 3 Backend-Services (Port 5000, 80, 443)"
|
||||||
echo -e " → Startet Flask-App mit --debug auf Port 5000"
|
echo -e " → Konfiguriert Autologin und Kiosk-Browser"
|
||||||
echo -e " → Testet Anwendungserreichbarkeit"
|
echo -e " → ${YELLOW}NEUSTART ERFORDERLICH!${NC}"
|
||||||
echo ""
|
echo ""
|
||||||
echo -e "${RED}0)${NC} Beenden"
|
echo -e "${RED}0)${NC} Beenden"
|
||||||
echo ""
|
echo ""
|
||||||
|
echo -e "${RED}⚠️ WARNUNG: Option 2 macht Raspberry Pi zu reinem Kiosk-System!${NC}"
|
||||||
echo -e "${BLUE}=================================================================${NC}"
|
echo -e "${BLUE}=================================================================${NC}"
|
||||||
echo -n "Ihre Wahl [0-2]: "
|
echo -n "Ihre Wahl [0-2]: "
|
||||||
}
|
}
|
||||||
@ -385,10 +770,11 @@ main() {
|
|||||||
mkdir -p "$(dirname "$INSTALL_LOG")"
|
mkdir -p "$(dirname "$INSTALL_LOG")"
|
||||||
touch "$INSTALL_LOG"
|
touch "$INSTALL_LOG"
|
||||||
|
|
||||||
log "=== MYP INSTALLER GESTARTET ==="
|
log "=== MYP VOLLSTÄNDIGER KIOSK-INSTALLER GESTARTET ==="
|
||||||
log "Arbeitsverzeichnis: $CURRENT_DIR"
|
log "Arbeitsverzeichnis: $CURRENT_DIR"
|
||||||
log "Zielverzeichnis: $APP_DIR"
|
log "Zielverzeichnis: $APP_DIR"
|
||||||
log "Service-Name: $SERVICE_NAME"
|
log "Kiosk-Services: $SERVICE_NAME_KIOSK, $SERVICE_NAME_HTTPS, $SERVICE_NAME_HTTP"
|
||||||
|
log "Kiosk-Benutzer: $KIOSK_USER"
|
||||||
log "System: $(uname -a)"
|
log "System: $(uname -a)"
|
||||||
log "Debian-Version: $(cat /etc/debian_version 2>/dev/null || echo 'Unbekannt')"
|
log "Debian-Version: $(cat /etc/debian_version 2>/dev/null || echo 'Unbekannt')"
|
||||||
|
|
||||||
@ -408,13 +794,26 @@ main() {
|
|||||||
;;
|
;;
|
||||||
2)
|
2)
|
||||||
clear
|
clear
|
||||||
log "=== OPTION 2: PRODUKTIONS-KIOSK-MODUS ==="
|
echo -e "${RED}⚠️ WARNUNG: Sie sind dabei, alle Desktop-Environments zu entfernen!${NC}"
|
||||||
setup_production_kiosk
|
echo -e "${YELLOW}Der Raspberry Pi wird zu einem reinen Kiosk-System umgebaut.${NC}"
|
||||||
|
echo -e "${BLUE}Nach der Installation startet automatisch der Kiosk-Browser.${NC}"
|
||||||
echo ""
|
echo ""
|
||||||
echo -e "${GREEN}✅ Produktions-Kiosk-Modus erfolgreich eingerichtet!${NC}"
|
echo -n "Sind Sie sicher? [ja/NEIN]: "
|
||||||
echo -e "${BLUE}ℹ️ Die Anwendung startet automatisch bei jedem Systemstart.${NC}"
|
read -r confirm
|
||||||
echo -e "${YELLOW}Drücken Sie Enter, um fortzufahren...${NC}"
|
|
||||||
read -r
|
if [ "$confirm" = "ja" ] || [ "$confirm" = "JA" ]; then
|
||||||
|
clear
|
||||||
|
log "=== OPTION 2: VOLLSTÄNDIGER KIOSK-MODUS ==="
|
||||||
|
setup_production_kiosk
|
||||||
|
echo ""
|
||||||
|
echo -e "${GREEN}✅ KIOSK-MODUS ERFOLGREICH EINGERICHTET!${NC}"
|
||||||
|
echo -e "${RED}🔄 NEUSTART JETZT ERFORDERLICH: sudo reboot${NC}"
|
||||||
|
echo -e "${YELLOW}Drücken Sie Enter, um fortzufahren...${NC}"
|
||||||
|
read -r
|
||||||
|
else
|
||||||
|
echo -e "${BLUE}Installation abgebrochen.${NC}"
|
||||||
|
sleep 2
|
||||||
|
fi
|
||||||
;;
|
;;
|
||||||
0)
|
0)
|
||||||
log "=== INSTALLER BEENDET ==="
|
log "=== INSTALLER BEENDET ==="
|
||||||
|
@ -385,12 +385,42 @@ def start_queue_manager():
|
|||||||
return manager
|
return manager
|
||||||
|
|
||||||
def stop_queue_manager():
|
def stop_queue_manager():
|
||||||
"""Stoppt den globalen Queue-Manager."""
|
"""Stoppt den globalen Queue-Manager definitiv und sicher."""
|
||||||
global _queue_manager_instance
|
global _queue_manager_instance
|
||||||
with _queue_manager_lock:
|
with _queue_manager_lock:
|
||||||
if _queue_manager_instance:
|
if _queue_manager_instance:
|
||||||
_queue_manager_instance.stop()
|
try:
|
||||||
_queue_manager_instance = None
|
queue_logger.info("🔄 Stoppe Queue-Manager...")
|
||||||
|
|
||||||
|
# Shutdown-Event setzen
|
||||||
|
_queue_manager_instance.shutdown_event.set()
|
||||||
|
|
||||||
|
# Monitor-Thread beenden
|
||||||
|
if (_queue_manager_instance.monitor_thread and
|
||||||
|
_queue_manager_instance.monitor_thread.is_alive()):
|
||||||
|
|
||||||
|
queue_logger.info("⏳ Warte auf Monitor-Thread...")
|
||||||
|
_queue_manager_instance.monitor_thread.join(timeout=5.0)
|
||||||
|
|
||||||
|
# Falls Thread nicht beendet wurde, forciere Beendigung
|
||||||
|
if _queue_manager_instance.monitor_thread.is_alive():
|
||||||
|
queue_logger.warning("⚠️ Monitor-Thread reagiert nicht - forciere Beendigung")
|
||||||
|
# Thread als Daemon markieren für automatische Beendigung
|
||||||
|
_queue_manager_instance.monitor_thread.daemon = True
|
||||||
|
|
||||||
|
# Status auf gestoppt setzen
|
||||||
|
_queue_manager_instance.is_running = False
|
||||||
|
|
||||||
|
# Explizit stop() aufrufen
|
||||||
|
_queue_manager_instance.stop()
|
||||||
|
|
||||||
|
queue_logger.info("✅ Queue-Manager erfolgreich gestoppt")
|
||||||
|
|
||||||
|
except Exception as e:
|
||||||
|
queue_logger.error(f"❌ Fehler beim Stoppen des Queue-Managers: {str(e)}")
|
||||||
|
finally:
|
||||||
|
# Instanz definitiv auf None setzen
|
||||||
|
_queue_manager_instance = None
|
||||||
|
|
||||||
# Automatisches Cleanup bei Prozess-Ende registrieren
|
# Automatisches Cleanup bei Prozess-Ende registrieren
|
||||||
atexit.register(stop_queue_manager)
|
atexit.register(stop_queue_manager)
|
Loading…
x
Reference in New Issue
Block a user