# Seguridad FOSFENO es un **aparato de directo**, no un servicio en internet. Está pensado para una red local: tú, tu móvil y el proyector. Esta página cuenta qué asume el diseño, qué pasa si la red no es de fiar, y cómo cerrarlo. ## El modelo de amenaza, en una frase Cualquiera que alcance `http:///` **manda sobre las visuales**. Por defecto no hay contraseña: es lo cómodo para casa, un ensayo o una red tuya, y es como funcionó desde el principio. Eso está bien en tu salón. En **la wifi de un bar o de un festival** significa que un desconocido puede: - Apagar o reiniciar el equipo en mitad de la sesión. - Cambiar de motor, de preset y de mapping. - **Ejecutar código** en el escenario, porque el editor de Hydra/GLSL es precisamente eso, y el navegador del kiosko arranca con permiso automático de **cámara y micrófono**. - Llenarte la tarjeta subiendo archivos a la galería. No es un fallo escondido: es la consecuencia de no pedir credenciales. La solución está abajo y son dos líneas de configuración. ## La clave compartida En `config.json`: ```json "auth": { "token": "loquesea-largo-y-tuyo" } ``` O sin tocar el archivo, por variable de entorno: ```bash FOSFENO_TOKEN=loquesea-largo-y-tuyo ./fosfeno ``` Con la clave puesta: - **El código QR del proyector ya la lleva dentro.** Escaneas y entras, igual que siempre. No hay que teclear nada. - Quien solo conozca la IP **no se conecta**: el WebSocket rechaza la conexión, así que no puede ni mirar el estado ni mandar órdenes. - Las subidas a la galería también la piden. - El escenario la recibe del propio servidor al abrirse. No hay nada que configurar en el navegador. La contrapartida: si escribes la dirección a mano tendrás que añadir `?k=tu-clave` al final. Por eso el QR es el camino cómodo. > Con `token` vacío (el valor de fábrica) todo funciona exactamente como antes. > Actívala cuando pinches fuera de casa. ## Lo que ya está cerrado Estas no dependen de que actives nada: | | | |---|---| | **Path traversal** | Las rutas de archivos (`/panel`, `/stage`, `/lib`, `/data`, `/pm/variantes`) resuelven y comprueban que no salen de su carpeta. Probado con `../`, `%2e%2e%2f`, doble codificación y rutas absolutas | | **Nombres de archivo subidos** | Pasan por `secure_filename` y una lista blanca de extensiones. No se puede escribir fuera de `data/videos` ni subir un `.sh` | | **Inyección de comandos** | Ningún `shell=True`, ningún `os.system`. Todos los procesos se lanzan con lista de argumentos | | **Rutas de presets de projectM** | La categoría y el visual vienen del panel, así que se validan contra la carpeta de presets antes de usarse | | **XSS en el panel** | Los nombres de clips, capas y favoritos se pintan con `textContent`, nunca con `innerHTML` | | **CORS** | El WebSocket solo acepta su **mismo origen**. Antes admitía cualquiera, así que una web abierta en el móvil de alguien de la sala podía mandar órdenes | | **Tamaño de subida** | 512 MB por archivo (antes 4 GB, suficiente para llenar una microSD en tres peticiones) | | **Payloads del WebSocket** | Los ajustes se filtran por lista blanca de claves y las capas del mapping se sanean antes de guardarse, así que no se puede meter basura en el estado ni en `data/mapping.json` | ## Lo que NO deberías hacer - **No lo expongas a internet.** Nada de abrir el puerto 80 en el router ni ponerle un túnel. No está pensado para eso y la clave compartida no es autenticación seria. - **No dejes el apagado remoto a mano de una red pública** sin clave. El instalador da permiso `sudo` sin contraseña para `reboot` y `poweroff` (`install.sh`), que es lo que hace que el botón del panel funcione. - **No pongas datos personales en `data/videos`.** Cualquiera que entre al panel puede listarlos y reproducirlos. ## Lo que no se sube al repositorio `.gitignore` deja fuera lo de cada instalación: `.venv/`, `*.log` (el log del servidor lleva IPs), `data/mapping.json`, `data/pm-favoritos.json`, `data/videos/*` y `data/presets-projectm/`. En el repo solo van código, documentación y los presets de fábrica. ## Si encuentras algo Es un proyecto pequeño de un hacklab: abre una incidencia en el Gitea del proyecto contando qué has visto y cómo reproducirlo.