# Photomaton LSDW - Guide complet > Projet photomaton de l'association **Les Sapins Du Web** (LSDW) > Events : Hop'N Bloc, anniversaires, etc. > Derniere mise a jour : Juin 2026 --- ## Table des matieres 1. [Hardware](#1-hardware) 2. [Software Stack](#2-software-stack) 3. [Architecture reseau](#3-architecture-reseau) 4. [Flux utilisateur](#4-flux-utilisateur) 5. [GPIO et bouton physique](#5-gpio-et-bouton-physique) 6. [Configuration photobooth-app](#6-configuration-photobooth-app) 7. [Impression (Canon Selphy CP1300)](#7-impression-canon-selphy-cp1300) 8. [Node-RED](#8-node-red) 9. [Analyse des problemes et optimisations](#9-analyse-des-problemes-et-optimisations) 10. [Guide de deploiement](#10-guide-de-deploiement) 11. [Fichiers du projet](#11-fichiers-du-projet) 12. [Maintenance et surveillance](#12-maintenance-et-surveillance) 13. [Questions en suspens](#13-questions-en-suspens) --- ## 1. Hardware | Composant | Modele | Notes | |-----------|--------|-------| | SBC | Raspberry Pi 4 (**2 Go RAM**) | Contrainte memoire forte | | OS | Raspberry Pi OS / Debian 13 Trixie | Reference 2025-12-04, pi-gen stage4 | | Camera | Camera Module 3 officielle | Backend picamera2, ratio 3:2 natif (4608x3072) | | Ecran | Moniteur/TV HDMI | Chromium kiosk mode (Wayland/labwc) | | Bouton | Bouton lumineux 12V + relay | GPIO23 (input) + GPIO12 (relay ON/OFF) | | LED Strip | NeoPixels WS2812 (35 LEDs) | GPIO18, feedback visuel pendant capture | | Imprimante 1 | Canon Selphy CP1300 (blanche) | USB, CUPS: `Canon_SELPHY_CP1300_usb_blanche` | | Imprimante 2 | Canon Selphy CP1300 (noire) | USB, CUPS: `Canon_SELPHY_CP1300_usb_noire` | | WiFi | Chip WiFi interne RPi4 | Hotspot via RaspAP | ### Format d'impression - Papier : **100 x 150 mm** (carte postale, 4x6 pouces) - Ratio : **3:2** (identique au capteur Camera Module 3) - Resolution minimum a 300 dpi : 1770 x 1182 px - Cadres PNG : **2000 x 1333 px** (ratio 3:2) --- ## 2. Software Stack ### Schema general ``` +----------------------------------------------------------+ | Navigateur Web | | Chromium kiosk (Wayland, labwc) | | ~/Desktop/photobooth-app.desktop | +----------------------------------------------------------+ | | | photobooth-app (:8083) Node-RED (:1880) | | via pipx venv via npm | | - Capture camera - Bouton GPIO23 (multi-clic) | | - Post-traitement - Relay bouton GPIO12 | | - Galerie + QR share - NeoPixels GPIO18 | | - Interface utilisateur - Dashboard admin impression | | - File attente SQLite | | - Gestion CUPS | | | +----------------------------------------------------------+ | Zoraxy (reverse proxy + TLS :443) | | ~/zoraxy/ | +----------------------------------------------------------+ | CUPS + Gutenprint | RaspAP (hotspot WiFi) | | Canon Selphy CP1300 x2 | lighttpd :8082 | +----------------------------------------------------------+ | uvicorn :8081 (API backend RaspAP) | +----------------------------------------------------------+ | Raspberry Pi OS / Debian 13 Trixie | +----------------------------------------------------------+ ``` ### Versions et chemins | Composant | Chemin / Info | |-----------|--------------| | photobooth-app | `~/.local/share/pipx/venvs/photobooth-app/` | | Donnees photobooth | `~/photobooth-data/` | | Node-RED | `~/.node-red/` | | Zoraxy | `~/zoraxy/` | | Config Zoraxy | `~/zoraxy/conf/proxy/` | | RaspAP API | `/etc/raspap/api/` (uvicorn :8081) | | Chromium | `/usr/bin/chromium` (pas chromium-browser, Trixie) | | Kiosk desktop | `~/Desktop/photobooth-app.desktop` | --- ## 3. Architecture reseau ### Ports en ecoute | Service | Port | Process | Role | |---------|------|---------|------| | SSH | 22 | sshd | Acces distant | | DNS | 53 | dnsmasq | RaspAP, resolution domaines locaux | | HTTP | 80 | zoraxy | Redirect -> HTTPS | | HTTPS | 443 | zoraxy | Reverse proxy principal | | CUPS | 631 | cupsd | Administration imprimantes | | Node-RED | 1880 | node-red | Dashboard admin + GPIO + NeoPixels | | Zoraxy admin | 5487 | zoraxy | Panel admin (localhost only) | | Zoraxy admin | 8001 | zoraxy | Panel admin (expose via sous-domaine) | | RaspAP API | 8081 | uvicorn/python3 | API backend RaspAP (/etc/raspap/api/) | | RaspAP | 8082 | lighttpd + php-fpm | Interface admin WiFi | | photobooth-app | 8083 | python (pipx) | Interface web principale | | ~~rpcbind~~ | ~~111~~ | ~~rpcbind~~ | **INUTILE - a desactiver** | ### Reverse proxy Zoraxy Zoraxy ecoute sur les ports 80 (HTTP redirect) et 443 (HTTPS) et route vers les services locaux : | Sous-domaine | Upstream | Service | Notes | |-------------|----------|---------|-------| | `photomaton.lessapinsduweb.com` | 127.0.0.1:8083 | photobooth-app | WebSocket ON, ChunkedTransfer OFF | | `photomaton-nodered.lessapinsduweb.com` | 127.0.0.1:1880 | Node-RED | Dashboard impression | | `photomaton-raspap.lessapinsduweb.com` | 127.0.0.1:8082 | RaspAP | Config WiFi | | `photomaton-zoraxy.lessapinsduweb.com` | 127.0.0.1:8001 | Zoraxy admin | Self-management | - Certificats TLS geres par Zoraxy - Chaque service gere sa propre authentification - `DisableChunkedTransferEncoding: true` sur le proxy photobooth (necessaire pour le livestream) ### WiFi (RaspAP) | Element | Valeur | |---------|--------| | Interface | wlan0 | | IP du Pi | 10.3.141.1 | | Plage DHCP | 10.3.141.50 - 10.3.141.254 (~200 clients) | | Masque | 255.255.255.0 | | Bail DHCP | 12h | | DNS | dnsmasq sur le Pi (port 53) | | Internet | **AUCUN** (captive portal) | ### Resolution DNS (dnsmasq) ``` # /etc/dnsmasq.d/090_custom_local_hotspot.conf address=/lessapinsduweb.com/10.3.141.1 # *.lessapinsduweb.com -> Pi address=/photomaton.lessapinsduweb.com/10.3.141.1 # explicite address=/#/127.0.0.1 # tout le reste -> null (pas d'internet) ``` Les telephones connectes au WiFi ne peuvent acceder qu'aux sous-domaines `*.lessapinsduweb.com`. Tout le reste est bloque (pas d'internet). --- ## 4. Flux utilisateur ### Prise de photo ``` Bouton physique (GPIO23) | v Node-RED (button-events: clic/double/triple/quadruple) | +--> Desactive relay bouton (GPIO12 = OFF) +--> NeoPixels: vert (countdown) +--> Appel API photobooth-app: GET /api/actions/image/{N} | v photobooth-app 1. Countdown (5s) affiche sur ecran 2. NeoPixels: blanc (flash) <-- webhook -> Node-RED 3. Capture Camera Module 3 (picamera2) 4. NeoPixels: violet (captured) 5. Post-traitement (cadre, remove_background si active) 6. Photo ajoutee a la galerie 7. NeoPixels: bleu (finished) puis vert apres 2s 8. Reactive relay bouton (GPIO12 = ON) 9. QR code affiche pour telecharger via WiFi ``` ### Recuperation de la photo (QR code) ``` 1. Telephone se connecte au WiFi "Photomaton" 2. Recoit IP en 10.3.141.x via DHCP, DNS = 10.3.141.1 3. Scan QR code -> https://photomaton.lessapinsduweb.com/sharepage/#?url=... 4. dnsmasq resout vers 10.3.141.1 (le Pi) 5. Zoraxy (:443) sert la page via HTTPS 6. photobooth-app (:8083) fournit la photo ``` ### Impression ``` Utilisateur: clic "Demander l'impression" dans galerie photobooth-app | v photobooth-app: share_command = curl Node-RED /api/photobooth-custom/ask_print | v Node-RED: 1. Recupere l'UID de la photo via API photobooth /api/mediacollection 2. Insere dans SQLite (photo-to-print.sqlite) 3. Affiche dans le dashboard admin (/dashboard) | v Admin (sur telephone via WiFi, https://photomaton-nodered.lessapinsduweb.com/dashboard): - Voit la demande dans le tableau avec preview photo - Clic "OK" = lance impression via script_print.sh - Clic "x" = annule la demande - Peut aussi cancel/clear les jobs CUPS, enable/disable imprimantes | v script_print.sh: 1. Verifie le ratio de l'image (crop 3:2 si necessaire) 2. Choisit l'imprimante idle (blanche ou noire, load-balancing) 3. Envoie le job via lp -d PRINTER -o landscape -o fit-to-page ``` --- ## 5. GPIO et bouton physique ### Mapping GPIO | GPIO | Pin physique | Fonction | Direction | Controle par | |------|-------------|----------|-----------|--------------| | 12 | 32 | Relay bouton lumineux 12V | Output | Node-RED | | 17 | 11 | Shutdown (maintien 2s) | Input | photobooth-app | | 18 | 12 | NeoPixels 35 LEDs WS2812 | Output | Node-RED (neopix.py, sudo) | | 20 | 38 | Job abort | Input | photobooth-app | | 22 | 15 | Job reject / Collage trigger | Input | photobooth-app | | 23 | 16 | Bouton physique principal | Input (pull-up) | Node-RED (button-events) | | 27 | 13 | Job next | Input | photobooth-app | ### Modes photo (bouton multi-clic sur GPIO23) | Clics | Mode | Action API | remove_background | |-------|------|-----------|-------------------| | 1 clic | HnB normal | `/api/actions/image/0` | Non | | 2 clics | HnB etoile | `/api/actions/image/1` | Oui | | 3 clics | HnB cailloux | `/api/actions/image/2` | Oui | | 4 clics | HnB light | `/api/actions/image/3` | Oui | | Appui long | Demande impression | `/api/share/actions/latest/0` | - | Le multi-clic est gere par le node `button-events` de Node-RED avec : - Intervalle clic : 500 ms - Intervalle appui long : 2000 ms - Debounce : 15 ms ### NeoPixels - Couleurs par evenement | Evenement | Couleur | Brightness | |-----------|---------|------------| | Countdown (counting) | Vert `#008000` | 100 | | Flash (capture) | Blanc `#FFFFFF` | 255 | | Captured | Violet `#8A2BE2` | 100 | | Finished | Bleu `#0000FF` | 100 | | Idle (apres 2s) | Vert `#008000` | 100 | --- ## 6. Configuration photobooth-app ### Parametres critiques (config originale vs optimisee) | Parametre | Avant (original) | Apres (optimise) | Impact | |-----------|-----------------|------------------|--------| | `logging_level` | `DEBUG` | `WARNING` | CPU+RAM en continu | | `full_still_length` | 4608 | 2304 | /4 RAM par image | | `CAPTURE_CAM_RESOLUTION` | 4608x3072 | 2304x1536 | /4 RAM capture | | `PREVIEW_CAM_RESOLUTION` | 2304x1536 | 1152x768 | /4 RAM preview | | `original_still_quality` | 100 | 90 | -35% taille fichiers | | `thumbnail_still_length` | 960 | 480 | Moins de RAM galerie | | `gpio_enabled` | false | true | GPIO natif photobooth-app | | `secret_key` | `ThisIsTheDefaultSecret` | A changer ! | Securite | ### Justification des resolutions - Camera Module 3 : capteur 4608x3072 (ratio 3:2) - Cadres PNG : 2000x1333 (ratio 3:2) - Impression Selphy 300dpi sur 100x150mm : besoin minimum 1770x1182 px - **2304x1536 est suffisant** : au-dessus du cadre (2000px) et de l'impression (1770px) - Ratio 3:2 conserve partout : pas de deformation ni de crop a l'impression ### Actions image (7 actions, config optimisee) | # | Nom | Cadre | remove_background | Fond | show_button | |---|-----|-------|-------------------|------|-------------| | 0 | HnB normal | hnb cadre final.png | Non | Non | **Oui** | | 1 | HnB etoile | hnb cadre final.png | Oui | background.jpg | Oui | | 2 | HnB cailloux | hnb cadre final.png | Oui | Wall-with-large-and-small-stones.jpg | Non | | 3 | HnB light | calque photos final.png | Oui | 2149243965.jpg | Non | | 4 | Normal image | Aucun | Non | Non | Non | | 5 | LULU | lulu-versaire2.png | Non | Non | Non | | 6 | LULU etoile | lulu-versaire2.png | Oui | background.jpg | Non | Actions supprimees (doublons) : `background stars`, `Hnb - Etoile - copy` ### Actions share (2 actions, config optimisee) | # | Nom | Commande | Visible | Usage | |---|-----|----------|---------|-------| | 0 | Demande d'impression | `curl http://127.0.0.1:1880/api/photobooth-custom/ask_print?filename={filename}` | Oui | File d'attente SQLite via Node-RED | | 1 | Impression directe | `/home/pi/photobooth-data/script/script_print.sh "{filename}" ...` | Non | Appelee par Node-RED quand l'admin valide | Actions supprimees : `Pouet` (test), `Mailing action` (demo), `Printing copies` (doublon) ### QR Share ```json { "enabled": false, "enabled_custom": true, "share_custom_qr_url": "https://photomaton.lessapinsduweb.com/sharepage/#?url=https://photomaton.lessapinsduweb.com/media/full/{identifier}" } ``` ### Kiosk (Chromium) Fichier : `~/Desktop/photobooth-app.desktop` ```ini [Desktop Entry] X-GNOME-Autostart-enabled=true X-GNOME-Autostart-Delay=120 Terminal=false Type=Application Name=Photobooth-App Exec=bash -c "sleep 60 && chromium --kiosk --accept-lang=fr-FR --incognito --password-store=basic --disable-features=Translate,OverscrollHistoryNavigation --noerrdialogs --disable-infobars --no-first-run --ozone-platform=wayland --enable-features=OverlayScrollbar --start-maximized http://127.0.0.1:8083/" StartupNotify=false ``` Points importants : - `--ozone-platform=wayland` : Wayland natif (pas X11) - Le binaire est `chromium` (pas `chromium-browser`) sous Trixie - Le desktop file est dans `~/Desktop/`, pas dans `~/.config/autostart/` --- ## 7. Impression (Canon Selphy CP1300) ### Configuration CUPS | Imprimante | Nom CUPS | Couleur | |-----------|---------|---------| | Selphy 1 | `Canon_SELPHY_CP1300_usb_blanche` | Blanche | | Selphy 2 | `Canon_SELPHY_CP1300_usb_noire` | Noire | Driver : Gutenprint (`printer-driver-gutenprint`) ### Script d'impression (`script_print.sh`) Le script optimise fait : 1. **Verifie le ratio** de l'image. Si c'est deja du 3:2 (cas normal), pas de crop. Sinon, crop avec ImageMagick. 2. **Load-balancing** entre les 2 imprimantes : - Si une est idle, utilise celle-la - Si aucune n'est idle, choisit celle avec le moins de jobs en attente - Fallback sur la blanche si les deux sont inaccessibles 3. **Envoie le job** via `lp -n COPIES -d PRINTER -o landscape -o fit-to-page` 4. **Nettoie** le fichier temporaire croppe apres 30 secondes 5. **Logs** via `logger` (visible avec `journalctl -t photomaton-print`) ### Commande d'impression directe (test) ```bash lp -d Canon_SELPHY_CP1300_usb_blanche -o landscape -o fit-to-page /chemin/vers/photo.jpg ``` ### Administration CUPS - Interface web : `http://localhost:631` - Via Node-RED dashboard : enable/disable imprimantes, cancel jobs - Via script : `scripts/cups-cleanup.sh` (genere par `setup-printer.sh`) --- ## 8. Node-RED ### Role dans le systeme Node-RED est **indispensable** dans le setup actuel. Il gere : 1. **Bouton physique** (GPIO23) : detection multi-clic via `button-events`, appel API photobooth-app 2. **Relay bouton** (GPIO12) : ON/OFF du bouton lumineux 12V pendant les captures 3. **NeoPixels** (GPIO18) : changement de couleur synchronise aux evenements photobooth 4. **Dashboard admin impression** : tableau des demandes, preview photos, boutons imprimer/annuler 5. **File d'attente SQLite** : stockage des demandes d'impression dans `photo-to-print.sqlite` 6. **Gestion CUPS** : etat imprimantes, enable/disable, cancel jobs ### Flows (onglets) | Tab | Nom | Fonction | |-----|-----|----------| | 1 | Photomaton | GPIO bouton, relay, declenchement photo, selection mode | | 2 | Flux 2 | Dashboard imprimantes (etat, enable/disable, jobs) | | 3 | Flux 3 | Webhook events photobooth -> NeoPixels + relay bouton | | 4 | Flux 4 | Controle NeoPixels direct (35 LEDs, GPIO18) | | 5 | Sqlite | File d'attente impression (SQLite, dashboard, CRUD) | ### Endpoints HTTP (Node-RED) | Endpoint | Methode | Usage | |----------|---------|-------| | `/api/photobooth/*` | GET | Webhook events photobooth (counting, capture, captured, finished) | | `/api/photobooth-custom/ask_print` | GET | Demande d'impression (appelee par photobooth-app) | | `/dashboard` | GET | Interface admin (impression, imprimantes, systeme) | ### Base SQLite - Fichier : `/home/pi/photobooth-data/photo-to-print.sqlite` - Table : `photoToPrint` (id, filename, uid, toPrint, printed, created_at) - L'admin voit les photos en attente dans le dashboard avec preview et peut imprimer ou annuler ### Migration vers Python ? **Non recommande.** Le gain serait de ~100 Mo de RAM, mais le cout de redeveloppement est eleve (dashboard, SQLite CRUD, GPIO multi-clic, NeoPixels sync, gestion CUPS). Les optimisations systeme et config liberent deja ~630 Mo sans rien recoder. --- ## 9. Analyse des problemes et optimisations ### Problemes rapportes 1. **Crashs frequents** 2. **Problemes d'impression** 3. **Memoire insuffisante (2 Go)** ### Consommation RAM mesuree (ps aux, au repos) | Service | RAM (Mo) | % du total | |---------|----------|-----------| | **Chromium** (kiosk + processus fils) | **~580** | 40% | | **Node-RED** | **171** | 12% | | **photobooth-app** | **142** | 10% | | **Zoraxy** | **99** | 7% | | **Desktop inutile** (pcmanfm, wf-panel, portails, gvfsd...) | **~231** | 16% | | Autres (labwc, pipewire, CUPS, dnsmasq, lighttpd, php-fpm...) | ~130 | 9% | | Kernel + systeme | ~100 | 7% | | **TOTAL** | **~1450** | **79%** | RAM disponible au repos : **~725 Mo** -- mais ca chute fortement pendant les captures, surtout avec `remove_background`. ### Causes des crashs identifiees | Cause | Impact | Correction | |-------|--------|------------| | `logging_level: DEBUG` | CPU+RAM constant, logs enormes | -> `WARNING` | | Resolution capture 4608x3072 (14 Mpx) | ~56 Mo par image en RAM | -> 2304x1536 (~14 Mo) | | `remove_background` (MODNet) sur 5/9 actions | +300-400 Mo RAM par traitement | Garder uniquement quand on change le fond | | `original_still_quality: 100` | Fichiers JPEG 2x plus gros | -> 90 | | Desktop inutile (pcmanfm, barre de taches, portails) | ~231 Mo gaspilles | Script `optimize-desktop.sh` | | Swappiness a 60 | Le systeme swappe trop tot | -> 10 | | Pas de swap fichier (seulement zram) | OOM kill si zram plein | Ajouter swapfile 1 Go | ### Plan d'optimisation | Optimisation | Script | Gain RAM estime | |-------------|--------|----------------| | Desactiver desktop inutile | `optimize-desktop.sh` | **~231 Mo** | | Reduire resolution capture | Config photobooth-app | **~42 Mo/capture** | | Reduire resolution preview | Config photobooth-app | **~11 Mo** | | `logging_level` DEBUG -> WARNING | Config photobooth-app | Variable (CPU + RAM) | | JPEG quality 100 -> 90 | Config photobooth-app | -35% I/O disque | | Desactiver services inutiles | `optimize-system.sh` | **~50 Mo** | | Swappiness 60 -> 10 | `optimize-system.sh` | Moins de swap inutile | | Swapfile 1 Go (filet de securite) | `optimize-system.sh` | Evite les OOM kills | | Limiter Node-RED a 256 Mo (cgroup) | `optimize-system.sh` | Protection fuites memoire | | Chromium optimise (process-per-site, JS heap) | Config kiosk | Reduction Chromium | ### Estimation apres optimisation ``` AVANT (mesure reelle): Chromium ~580 Mo Node-RED ~171 Mo photobooth-app ~142 Mo Zoraxy ~99 Mo Desktop inutile ~231 Mo Autres ~230 Mo -------------------------------- TOTAL ~1453 Mo / 1843 Mo dispo Marge disponible: ~390 Mo Marge pendant capture: ~0 Mo (crash!) APRES optimisation: Chromium (optimise) ~400 Mo (options memoire) Node-RED (cgroup 256 Mo) ~171 Mo (max 256 Mo) photobooth-app ~142 Mo Zoraxy ~99 Mo Desktop inutile 0 Mo (desactive) Autres (sans services inut) ~180 Mo -------------------------------- TOTAL ~992 Mo / 1843 Mo dispo Marge disponible: ~851 Mo + swapfile 1 Go en filet de securite + images 4x plus petites en RAM pendant capture -> Suffisant meme avec remove_background (~300 Mo) ``` --- ## 10. Guide de deploiement ### Prerequis - Acces SSH au Raspberry Pi - Copier le dossier `photomaton/` sur le Pi ### Etape 1 : Optimisation systeme ```bash sudo bash scripts/optimize-system.sh sudo reboot ``` Ce script : - Ajoute un swapfile 1 Go (complement au zram existant) - Baisse le swappiness de 60 a 10 - Configure gpu_mem a 128 Mo - Desactive les services inutiles (bluetooth, ModemManager, rpcbind, apt timers...) - Desactive le Bluetooth au niveau kernel - Optimise les parametres memoire kernel (vfs_cache_pressure, dirty_ratio) - Limite Node-RED a 256 Mo RAM (cgroup systemd) - Optimise les parametres reseau ### Etape 2 : Optimisation desktop ```bash sudo bash scripts/optimize-desktop.sh sudo reboot ``` Ce script : - Cree un autostart labwc minimal (que Chromium + pipewire) - Desactive pcmanfm, wf-panel-pi, portails desktop, polkit, gvfsd - Desactive ModemManager, accounts-daemon, colord, rpcbind, upower - Reduit les workers php-fpm (RaspAP) a 2 **Reversible** : `sudo bash scripts/optimize-desktop.sh --restore` ### Etape 3 : Script d'impression ```bash cp scripts/script_print.sh /home/pi/photobooth-data/script/script_print.sh chmod +x /home/pi/photobooth-data/script/script_print.sh ``` ### Etape 4 : Configuration photobooth-app Deux options : **Option A** : Appliquer via l'interface admin (`https://photomaton.lessapinsduweb.com/admin`) - Modifier chaque parametre un par un en suivant le tableau de la section 6 **Option B** : Remplacer le fichier de config - Copier `config/photobooth-config-optimized.json` dans le dossier de config de photobooth-app - Supprimer les champs `_comment`, `_OPTI_*` (ce sont des annotations) - Redemarrer photobooth-app **Important** : Generer une vraie `secret_key` : ```bash python3 -c "import secrets; print(secrets.token_hex(32))" ``` ### Etape 5 : Services systemd (watchdog + maintenance) ```bash # Service photobooth-app (utilisateur) cp systemd/photobooth-app.service ~/.config/systemd/user/ systemctl --user daemon-reload systemctl --user enable photobooth-app # Watchdog (systeme) sudo cp systemd/photobooth-watchdog.service /etc/systemd/system/ sudo cp systemd/photobooth-watchdog.timer /etc/systemd/system/ # Editer les chemins dans les .service si necessaire sudo systemctl daemon-reload sudo systemctl enable photobooth-watchdog.timer sudo systemctl start photobooth-watchdog.timer # Maintenance quotidienne (systeme) sudo cp systemd/photobooth-maintenance.service /etc/systemd/system/ sudo cp systemd/photobooth-maintenance.timer /etc/systemd/system/ sudo systemctl daemon-reload sudo systemctl enable photobooth-maintenance.timer sudo systemctl start photobooth-maintenance.timer ``` ### Etape 6 : Verification ```bash bash scripts/health-check.sh ``` ### Quick wins immediats (sans script) Si tu veux appliquer les corrections les plus impactantes maintenant sans lancer les scripts complets : ```bash # 1. Baisser le swappiness (gain immediat) sudo sysctl vm.swappiness=10 echo 'vm.swappiness=10' | sudo tee /etc/sysctl.d/99-photomaton-swap.conf # 2. Desactiver rpcbind (inutile) sudo systemctl disable rpcbind.service rpcbind.socket sudo systemctl stop rpcbind.service rpcbind.socket # 3. Desactiver ModemManager (inutile) sudo systemctl disable ModemManager.service sudo systemctl stop ModemManager.service # 4. Changer le logging_level dans photobooth-app admin # http://localhost:8083/admin -> common -> logging_level -> WARNING ``` --- ## 11. Fichiers du projet ``` photomaton/ scripts/ optimize-system.sh # Optimisation OS (swap, kernel, services) optimize-desktop.sh # Desactiver le desktop inutile (~231 Mo) setup-printer.sh # Configuration CUPS + Selphy CP1300 setup-photobooth.sh # Installation complete (master script) script_print.sh # Script d'impression optimise (load-balancing) health-check.sh # Watchdog / surveillance sante maintenance.sh # Nettoyage automatique quotidien config/ photobooth-config-backup.json # Config photobooth-app originale photobooth-config-optimized.json # Config optimisee (avec annotations _OPTI_) gpio-notes.conf # Documentation GPIO complete zoraxy-notes.conf # Cartographie reseau Zoraxy nodered-flows-backup.json # Reference backup flows Node-RED systemd/ photobooth-app.service # Service robuste (auto-restart, limites RAM) photobooth-watchdog.service # Health check automatique photobooth-watchdog.timer # Toutes les 2 minutes photobooth-maintenance.service # Nettoyage quotidien photobooth-maintenance.timer # A 4h du matin docs/ GUIDE-COMPLET.md # Ce fichier ARCHITECTURE.md # Schema d'architecture ANALYSE-CONFIG.md # Analyse detaillee des problemes ``` ### Fichiers sur le Pi ``` /home/pi/ photobooth-data/ media/ processed_full/ # Photos traitees (pleine resolution) script/ script_print.sh # Script d'impression log/ # Logs quotidiens photobooth-app photo-to-print.sqlite # File d'attente impression (Node-RED) userdata/ hopnbloc/ frames/ # Cadres PNG 2000x1333 (ratio 3:2) hnb cadre final.png calque photos final.png backgrounds/ # Fonds pour remove_background Wall-with-large-and-small-stones.jpg 2149243965.jpg LSDW/ lulu-versaire2.png # Cadre anniversaire logo/logo.jpeg # Logo LSDW demoassets/ backgrounds/background.jpg # Fond etoiles frames/ # Cadres demo .node-red/ # Node-RED flows.json # Flows (5 onglets) node_modules/ node-red-node-pi-gpio/ # GPIO nodes node-red-node-pi-neopixel/ # NeoPixels nodes zoraxy/ zoraxy # Binaire start.sh # Script de demarrage conf/proxy/ # Configs reverse proxy ws2812/ # Ancien test NeoPixels (inactif) Desktop/ photobooth-app.desktop # Autostart Chromium kiosk ``` --- ## 12. Maintenance et surveillance ### Watchdog (health-check.sh) Execute toutes les 2 minutes par `photobooth-watchdog.timer`, verifie : - **Memoire** : alerte si < 100 Mo dispo, vide les caches si critique - **Temperature CPU** : alerte si > 70C, erreur si > 80C - **photobooth-app** : verifie si le service tourne ET si l'interface web repond (HTTP 200) - **Imprimantes** : verifie CUPS, reactive les imprimantes desactivees, nettoie les jobs bloques - **Espace disque** : alerte si > 80%, nettoyage d'urgence si > 90% - **Camera** : verifie que la camera est detectee par libcamera Si photobooth-app ne repond pas, le watchdog le relance automatiquement (max 3 tentatives). ### Maintenance quotidienne (maintenance.sh) Execute tous les jours a 4h par `photobooth-maintenance.timer` : - Nettoyage des vieux logs photobooth (> 7 jours) - Nettoyage des logs systeme comprimes - Limitation journald a 50 Mo - Nettoyage des jobs CUPS bloques - Reactivation des imprimantes desactivees - Nettoyage cache apt - Rapport d'etat (espace disque, nombre de photos, uptime) ### Service systemd photobooth-app Le service `photobooth-app.service` inclut : - `Restart=always` avec 5s de delai - `MemoryMax=1500M` : kill si depasse 1.5 Go (protection OOM) - `MemoryHigh=1200M` : avertissement a 1.2 Go - `WatchdogSec=120` : watchdog integre systemd - `StartLimitBurst=5` / `StartLimitIntervalSec=300` : max 5 redemarrages en 5 min ### Commandes utiles ```bash # Logs photobooth-app journalctl --user --unit=photobooth-app -n 200 --no-pager # Logs impression journalctl -t photomaton-print --no-pager # Logs watchdog journalctl -t photomaton-watchdog --no-pager # Etat des services systemctl --user status photobooth-app systemctl status photobooth-watchdog.timer systemctl status photobooth-maintenance.timer # Etat imprimantes lpstat -p # Etat memoire free -h zramctl # Etat des processus par RAM ps aux --sort=-%mem | head -20 # Health check manuel bash scripts/health-check.sh ``` --- ## 13. Questions en suspens - [x] ~~**NeoPixels doublon**~~ : RESOLU. uvicorn (:8081) est l'API backend de RaspAP (`/etc/raspap/api/`), pas les NeoPixels. Les NeoPixels sont geres uniquement par `neopix.py` via Node-RED. Le dossier `~/ws2812/` est un ancien test inactif. - [ ] **Tester la config optimisee** en conditions reelles lors d'un event. - [ ] **Generer une vraie `secret_key`** pour photobooth-app (remplacer `ThisIsTheDefaultSecret`). - [ ] **Verifier le captive portal** : `address=/#/127.0.0.1` redirige tout domaine inconnu vers localhost du telephone (pas vers le Pi). Les telephones ne detecteront pas automatiquement un portail captif. Si besoin d'une page d'accueil, rediriger vers 10.3.141.1 a la place. - [ ] **Verifier les cadres PNG** des autres actions (LULU, calque photos final.png) pour confirmer qu'ils sont aussi en ratio 3:2 et en resolution ~2000px.