IoPlay

IoPlay Suite

MANUAL TÉCNICO & ARQUITECTURA
Especificación de Ingeniería v1.0

Manual Técnico & Arquitectura del Software

Documentación de bajo nivel sobre el desacoplamiento de componentes, proxies inversos, persistencia en SQLite (WAL), indexación concurrente en Python y protocolos de comunicación TR-069 CWMP.

🏗️ 1. Topología del Sistema

La suite opera bajo un patrón de Microservicios Desacoplados en ejecución nativa sobre el sistema operativo Linux (Bare-Metal). Los microservicios de backend no están expuestos a Internet y se comunican a través de un proxy inverso autenticado.

🌐

Navegador del Usuario / Cliente

Tráfico Web Externo Autenticado
Puerto Público: 5540 Protocolo: HTTP / HTTPS Sesión Activa Requerida
▼
🛡️

Servidor Nginx + PHP-FPM 8.3/8.4 (IoPlay Customers)

Enrutador MVC & Puerta de Enlace de Seguridad Unificada (Puerto 5540)
CONTROL DE ACCESO Sesión PHP ($_SESSION['auth_user']) + OTP
PROXY INVERSO ProxyController.php reenvía /dcm y /acs
PERSISTENCIA LOCAL SQLite: users.db & audit.db (WAL)
127.0.0.1:5541 (PM2 / DCM)
▼
127.0.0.1:5542 (PM2 / ACS)
▼
📑

IoPlay DCM (Puerto 5541)

Visor Documental & Indexador
  • Runtime: Python 3.12 (Gunicorn 3w / PM2)
  • Motor: Flask + Watchdog (Tiempo Real)
  • Base de Datos: facturas_index.db (SQLite)
  • Almacenamiento: /cableexito y /infobox
📶

IoPlay ACS (Puerto 5542)

Gestión TR-069 & Control WiFi
  • Runtime: Python 3.12 (Gunicorn 3w / PM2)
  • Motor: Flask + Requests Proxy
  • Concentrador: GenieACS (15.235.32.113:5502)
  • Protocolo: CWMP / TR-069 Bearer Token

🔌 2. Microservicios, Runtime y Puertos

Componente Runtime / Framework Puerto / Socket Aislamiento
IoPlay Customers PHP 8.3/8.4-FPM + Nginx 0.0.0.0:5540 Público (Portal Web Autenticado)
IoPlay DCM Python 3.12 (Gunicorn 3w / PM2) 127.0.0.1:5541 Privado / Loopback Estricto
IoPlay ACS Python 3.12 (Gunicorn 3w / PM2) 127.0.0.1:5542 Privado / Loopback Estricto
Reservado / Soporte Microservicio / Tooling 127.0.0.1:5543 Privado / Diagnóstico
Servidor IoACS GenieACS Remote API 15.235.32.113:5502 Conexión Tokenizada Backend-to-Backend

🗄️ 3. Esquema de Bases de Datos SQLite 3 (WAL Mode)

La suite no requiere servidores MySQL ni bases de datos externas pesadas; utiliza motores SQLite 3 embebidos configurados con PRAGMA journal_mode = WAL; y PRAGMA synchronous = NORMAL; para soportar lecturas y escrituras concurrentes sin bloqueo de hilos.

A. Base de Datos de Facturas e Indexador (facturas_index.db)

SQL Schema CREATE TABLE IF NOT EXISTS invoices_index ( id INTEGER PRIMARY KEY AUTOINCREMENT, customer_id TEXT NOT NULL, document_date TEXT NOT NULL, year INTEGER NOT NULL, month INTEGER NOT NULL, document_type TEXT DEFAULT 'Facturas', cableoperador TEXT, agencia TEXT, file_name TEXT NOT NULL, file_relative_path TEXT UNIQUE NOT NULL, file_full_path TEXT NOT NULL, file_size INTEGER, file_mtime REAL, indexed_at DATETIME DEFAULT CURRENT_TIMESTAMP ); CREATE INDEX idx_customer_date ON invoices_index(customer_id, document_date DESC); CREATE INDEX idx_customer_ym ON invoices_index(customer_id, year, month); CREATE INDEX idx_doc_type ON invoices_index(document_type); CREATE INDEX idx_rel_path ON invoices_index(file_relative_path);

B. Base de Datos de Usuarios y Auditoría

  • ioplay-customers/data/users.db: Almacena usuarios administrativos y contraseñas hasheadas con algoritmo BCRYPT (password_hash).
  • ioplay-customers/data/audit.db: Registro inmutable de consultas realizadas por operadores (IP, suscriptor consultado, fecha/hora, acción).

🔄 4. Proxy Inverso y Enrutamiento Seguro (PHP)

Para evitar que el navegador del usuario tenga que acceder a múltiples puertos o servidores, ProxyController.php actúa como puerta de enlace unificada:

ProxyController.php // Rutas /dcm/* -> Reenvía internamente a 127.0.0.1:4000 // Rutas /acs/* -> Reenvía internamente a 127.0.0.1:5542 protected function requireAuth(string $subpath = '') { if (str_starts_with(ltrim($subpath, '/'), 'static/')) return; if (empty($_SESSION['auth_user'])) { header('Location: /login'); exit; } }

El controlador reescribe al vuelo las cabeceras, rutas relativas y llamadas API en el HTML/JS resultante para garantizar que el navegador siempre mantenga la sesión bajo el mismo dominio y puerto 5540.

⚙️ 5. Motor de Indexación DCM (Python)

El motor ioplay-dcm monitorea recursivamente hasta 9 rutas físicas de almacenamiento documental (ej: /var/www/html/cableexito/documentosdigitales y /var/www/html/infobox/documentosdigitales):

  • Watchdog Observer: Detecta eventos de creación y modificación de archivos en el sistema de archivos del servidor.
  • Extractor Regex de Metadatos: Parsea el nombre del archivo PDF para extraer automáticamente el número de abonado/cédula, tipo documental (Factura, Contrato, Orden), año y mes.
  • Upsert Atómico: Realiza inserciones con cláusula ON CONFLICT(file_relative_path) DO UPDATE para actualizar modificaciones sin generar duplicados.

📡 6. Motor TR-069 & GenieACS (IoPlay ACS)

El microservicio ioplay-acs se comunica con el concentrador TR-069 remoto utilizando tokens Bearer y manejando normalización de seriales de fabricantes:

VENDOR_MAP VENDOR_MAP = { "opti": "4f505449", # Optictimes GPON "cdtc": "43445443", # CDTech / C-Data "hwtc": "48575443", # Huawei Technologies "zteg": "5a544547", # ZTE Corporation "vsol": "56534f4c", # V-SOL GPON }

Esto permite buscar equipos indistintamente si el CRM o el usuario ingresa el serial en formato ASCII (OPTI4B5B715B) o en formato Hexadecimal (4F5054494B5B715B).

🛡️ 7. Mecanismos de Seguridad y Hardening

  • Aislamiento de Raíz Web: Nginx solo sirve la carpeta /public. Los directorios de código, scripts y bases de datos .db son inaccesibles por HTTP.
  • Consultas Parametrizadas: 100% de las consultas SQL en PHP (PDO) y Python (sqlite3) usan parámetros vinculados, neutralizando cualquier intento de inyección SQL.
  • Ocultamiento de Credenciales: Los tokens de CRM y TR-069 residen en los archivos .env y nunca se transmiten al cliente.