Plan: Monitoreo en Tiempo Real + Sistema de MIBs Mejorado
Fecha: 21-02-2026 Estado: Planificado Prioridad: Alta Versión objetivo: v1.1.0+
Contexto
Situacion actual
- Monitoreo: SNMP polling cada 60s via Agent Sentinel → SQLite → REST push → VictoriaMetrics → Browser polling 30s
- Latencia total: 60-90s device-to-browser
- MIBs: Descarga online via pysmi desde
pysnmp.github.io→ compilacion ASN.1 → cache filesystem - Deep Discovery: OIDs hardcodeados en migration seed (0005) por vendor
Problema
- Latencia alta: 60-90s es inaceptable para monitoreo WiFi (client associations, roaming, interferencia)
- MIBs dependen de internet: En produccion SaaS, cold start de 10-30s por compilacion MIB
- SNMP limitado: Los fabricantes modernos (Xirrus XMS-E, cnMaestro, UniFi, Meraki, Aruba Central) usan WebSocket en sus plataformas cloud para datos en tiempo real
- OIDs estaticos: Agregar soporte para nuevo vendor requiere migration + deploy
Objetivo
- Reducir latencia device-to-browser de 60-90s a 1-15s
- Eliminar dependencia de internet para MIBs
- Soporte multi-protocolo: SNMP (legacy) + WebSocket/REST (moderno) + gNMI (enterprise switches)
- OIDs editables sin deploy
Arquitectura Objetivo
Red Local del Cliente CreaRack SaaS
┌────────────────────────────────┐ ┌──────────────────────────┐
│ │ │ │
│ [Cambium APs] ──┐ │ │ Django Channels │
│ [Xirrus APs] ──┤ SNMP 15s │ │ ┌─────────────────────┐ │
│ [Cisco SW] ──┤ │ │ │ WS Consumer │ │
│ [Arista SW] ──┘ │ │ │ (real-time push │──── WS ────▶ Browser
│ │ │ │ to browsers) │ │ (1-2s latency)
│ [Cambium APs] ─── Syslog ──▶│ │ └─────────────────────┘ │
│ [Xirrus APs] ─── Syslog ──▶│ │ │
│ [Cualquiera] ─── Traps ───▶│ │ VictoriaMetrics │
│ │ │ (time-series storage) │
│ [Cisco IOS-XE] ── gNMI ────▶│ │ │
│ [Arista EOS] ── gNMI ────▶│ └──────────────────────────┘
│ [Juniper] ── gNMI ────▶│ ▲
│ │ │ WebSocket
│ [MikroTik] ─── REST API ──▶│ │ (existente)
│ [FortiGate] ─── REST API ──▶│ │
│ │ ┌──────────┴───────────────┐
│ CreaRackAgent.exe │ │ │
│ ┌─────────────────────────┐ │ │ Multi-Protocol │
│ │ Multi-Protocol Engine │ │ │ Collector │
│ │ ├── SNMPWorker (15/60s)│──┼──────│ ├── Metrics → VM │
│ │ ├── SyslogReceiver │ │ │ ├── Events → WS push │
│ │ ├── TrapReceiver │ │ │ └── SQLite (offline) │
│ │ ├── gNMISubscriber │ │ │ │
│ │ └── RESTPoller │ │ └──────────────────────────┘
│ └─────────────────────────┘ │
└────────────────────────────────┘
Latencia por protocolo:
SNMP fast: 15-30s (OIDs ligeros cada 15s)
Syslog: <1s (event push, UDP)
SNMP Traps: <1s (event push, UDP)
gNMI: 1-10s (streaming subscription)
REST: 10-15s (polling directo)
WS browser: 1-2s (Django Channels push)
Fases de Implementacion
Fase 1: Quick Wins — SNMP Adaptativo + WS Browser Push (3-4 dias)
Objetivo: Reducir latencia de 60-90s a 15-30s sin dependencias nuevas.
1.1 SNMP Frecuencia Adaptativa (~50 lineas)
Archivos: terminal/agent/sentinel_scheduler.py
Concepto: Dos intervalos por target segun tipo de OID.
OIDs ligeros (15s): connected_clients, associatedClients, ifOperStatus
OIDs pesados (60s): ifHCInOctets, ifHCOutOctets, ifTable completa, vendor extras
Cambios:
SentinelScheduler: Nuevo loop_fast_snmp_loop(interval=15)para OIDs ligeros- Mantener
_snmp_loop(interval=60)para contadores de bandwidth - Configuracion en
VendorProfile.fast_poll_oids(lista de OIDs para poll rapido) - Agent recibe config via WebSocket (mismo patron que
monitoring_oids)
Resultado: Client count actualizado cada 15s en Wireless Monitor.
1.2 WebSocket Push al Browser (~100 lineas)
Archivos: monitoring/consumers.py (nuevo consumer), static/js/pages/wireless/WirelessDetail.js
Concepto: Cuando el Agent envia metricas via REST/WS, el SaaS las forwardea al browser sin esperar polling.
# monitoring/consumers.py
class WirelessMonitorConsumer(AsyncJsonWebsocketConsumer):
async def connect(self):
self.org_id = self.scope["user"].organization_id
await self.channel_layer.group_add(f"wireless_{self.org_id}", self.channel_name)
await self.accept()
async def wireless_update(self, event):
await self.send_json(event["data"])
# En receive_bulk_metrics (existente), anadir:
channel_layer = get_channel_layer()
await channel_layer.group_send(f"wireless_{org_id}", {
"type": "wireless.update",
"data": {"target_id": t.id, "metric": metric_type, "value": value, "ts": ts}
})
Frontend: WirelessDetail.js abre WS connection, actualiza charts/tablas en tiempo real sin setInterval polling.
Resultado: Metricas aparecen en browser 1-2s despues de que el Agent las envia.
1.3 MIBs Estandar Bundleados (~2 horas)
Archivos: Dockerfile, network/services/mib_manager.py
Pre-compilar en Docker build stage:
- IF-MIB, HOST-RESOURCES-MIB, ENTITY-MIB, Q-BRIDGE-MIB
- SNMPv2-MIB, SNMP-FRAMEWORK-MIB
- BRIDGE-MIB, IP-MIB
Resultado: 0s descarga, 0 network calls para 80% de discoveries. +15MB imagen Docker.
MibManager.ensure_mibs() ya checkea cache local primero → zero cambios funcionales.
Fase 2: Syslog + SNMP Traps — Eventos en Tiempo Real (2-3 dias)
Objetivo: Eventos WiFi (association, disassociation, roaming) en <1s.
2.1 Syslog Receiver en Agent (~80 lineas)
Archivos: terminal/agent/syslog_receiver.py (nuevo)
class SyslogReceiver(asyncio.DatagramProtocol):
"""UDP syslog receiver (RFC 5424/3164). Runs on port 514."""
def datagram_received(self, data, addr):
message = data.decode('utf-8', errors='replace')
parsed = self._parse_syslog(message)
# Forward via callback to Sentinel for SaaS push
if self.on_event:
asyncio.ensure_future(self.on_event(addr[0], parsed))
- Puerto: 514 UDP (configurable)
- Parser: RFC 5424 + RFC 3164 (los dos formatos comunes)
- Eventos utiles: client association, disassociation, auth failure, channel change, AP reboot
- Forward: Via SyncManager existente → SaaS → WS push a browser
Configuracion en dispositivos:
- Cambium: System > Syslog > Remote Server → IP del Agent
- Xirrus: CLI
syslog-host <agent-ip>
2.2 SNMP Trap Receiver en Agent (~100 lineas)
Archivos: terminal/agent/trap_receiver.py (nuevo)
Usa pysnmp (ya en el Agent) para escuchar traps en UDP 162:
- linkUp/linkDown (RFC 1215)
- authenticationFailure
- Vendor-specific traps (Cambium, Xirrus)
Complementario al syslog — algunos dispositivos solo soportan traps, no syslog externo.
2.3 Modelo de Eventos en SaaS (~60 lineas)
Archivos: monitoring/api.py, nuevo endpoint
# POST /api/agent/events (bulk)
# Payload: [{"ip": "x.x.x.x", "type": "client_assoc", "data": {...}, "ts": 1234567890}, ...]
- Almacenar en VictoriaMetrics como metricas de tipo event
- Forward via Django Channels al browser para actualizacion instantanea
- Opcional: Tabla de eventos en Wireless Monitor (ultimos 100 eventos por AP)
Fase 3: gNMI Streaming para Switches Enterprise (3-4 dias)
Objetivo: Monitoreo de switches Cisco/Arista/Juniper con latencia 1-10s via streaming telemetry.
3.1 gNMI Subscriber en Agent (~200 lineas)
Archivos: terminal/agent/gnmi_subscriber.py (nuevo)
Dependencia nueva: pygnmi + grpcio (BSD license, +15-20MB Agent binary)
from pygnmi.client import gNMIclient
class GnmiSubscriber:
async def subscribe(self, target_ip, port, username, password, paths, interval=10):
"""Subscribe to gNMI streaming telemetry."""
subscribe_config = {
'subscription': [
{'path': path, 'mode': 'sample', 'sample_interval': interval * 10**9}
for path in paths
],
'mode': 'stream',
'encoding': 'json'
}
# Run in thread (grpcio is sync)
# Forward updates to SyncManager
OpenConfig paths estandar:
interfaces/interface/state/counters— bandwidth, errors, discardscomponents/component/state/temperature— temperaturassystem/cpus/cpu/state— CPU usagesystem/memory/state— memoria
3.2 Configuracion en DeviceProfile/VendorProfile
Archivos: network/models.py
Nuevo campo en VendorProfile:
monitoring_protocols = JSONField(default=list) # ["snmp", "gnmi", "rest", "syslog"]
gnmi_config = JSONField(default=dict) # {"port": 6030, "paths": [...], "encoding": "json"}
El Agent auto-selecciona el mejor protocolo disponible por dispositivo.
3.3 Build Agent con grpcio
Archivos: build_agent.bat
Agregar pygnmi y grpcio a dependencias + hidden imports.
Impact: Agent binary +15-20MB (~40MB → ~60MB).
Fase 4: REST API Poller Multi-Vendor (2 dias)
Objetivo: Monitoreo de MikroTik (REST API v7.1+) y FortiGate sin SNMP.
4.1 REST Poller en Agent (~100 lineas)
Archivos: terminal/agent/rest_poller.py (nuevo)
- Usa
aiohttp(ya en el Agent) - MikroTik:
GET /rest/interface,GET /rest/system/resource - FortiGate:
GET /api/v2/monitor/system/resource/usage - Configurable por vendor via
VendorProfile.rest_api_config
4.2 VendorProfile REST Config
rest_api_config = JSONField(default=dict)
# Ejemplo MikroTik:
# {
# "base_url": "https://{ip}/rest",
# "auth": "basic", # basic, token, api_key
# "endpoints": {
# "interfaces": "/interface",
# "system": "/system/resource",
# "wireless": "/interface/wireless/registration-table"
# },
# "interval": 10
# }
Fase 5: Admin UI para OIDs + MIB Packages (2-3 dias)
Objetivo: Eliminar OIDs hardcodeados en migrations, gestionar MIBs sin deploy.
5.1 Admin UI para OID Management
Mover deep_discovery_oids y monitoring_oids de seed migration a UI editable:
- Django Admin: VendorProfile ya tiene los campos JSONField
- Crear vista admin personalizada con JSON editor por categoria
- Import/Export JSON para backup y compartir entre instancias
5.2 Vendor MIB Packages Pre-compilados
Management command: ./manage.py build-vendor-mibs
- Lee
VendorProfile.mib_modulesde DB - Compila via pysmi a Python
- Genera tarball:
vendor_mibs.tar.gz - Docker COPY en build stage
Resultado: 0 network calls para vendor MIBs, 0s cold start.
5.3 Smart OID Discovery (futuro)
Service que walk el arbol enterprise de un dispositivo, clasifica OIDs por categoria (cpu, memory, wireless, etc.), y sugiere al usuario cuales monitorear.
- Walk:
1.3.6.1.4.1.{enterprise_id}.* - Clasificar por nombre MIB + patrones de valor
- UI: “Encontrados 5 OIDs de CPU, 3 de memoria — seleccionar para monitoreo”
- Guardar en
DeviceProfile.custom_monitoring_oids
Resumen de Fases
| Fase | Descripcion | Esfuerzo | Deps nuevas | Latencia resultante |
|---|---|---|---|---|
| 1 | SNMP adaptativo (15/60s) + WS browser push + MIBs bundleados | 3-4 dias | Ninguna | 15-30s |
| 2 | Syslog receiver + SNMP Trap receiver + modelo eventos | 2-3 dias | Ninguna | <1s (eventos) |
| 3 | gNMI streaming (Cisco/Arista/Juniper) | 3-4 dias | pygnmi, grpcio (+20MB) | 1-10s (switches) |
| 4 | REST API poller (MikroTik, FortiGate) | 2 dias | Ninguna | 10-15s |
| 5 | Admin UI OIDs + MIB packages + Smart Discovery | 2-3 dias | Ninguna | N/A (DX mejora) |
Total estimado: 12-16 dias de desarrollo
Prioridad de Implementacion
SEMANA 1-2: Fase 1 (SNMP fast + WS push + MIBs)
→ Impacto inmediato: 60-90s → 15-30s
→ Zero dependencias nuevas
→ Wireless Monitor se actualiza en near real-time
SEMANA 2-3: Fase 2 (Syslog + Traps)
→ Eventos WiFi en <1s (association, roaming)
→ Tabla de eventos en Wireless Monitor
→ Alertas instantaneas
SEMANA 3-4: Fase 5 (Admin UI + MIBs)
→ Developer experience
→ Eliminar dependencia internet para MIBs
→ Vendors editables sin deploy
SEMANA 5-6: Fase 3 (gNMI)
→ Switches enterprise con streaming
→ Solo para clientes con Cisco/Arista/Juniper
FUTURO: Fase 4 (REST multi-vendor)
→ MikroTik, FortiGate
→ Bajo prioridad (SNMP cubre estos)
Compatibilidad hacia atras
- Sin Agent: SaaS usa su propia ruta SNMP (como hasta ahora)
- Agent viejo: Nuevos endpoints dan 404 → fallback a SNMP polling 60s
- Dispositivos sin syslog/traps: SNMP sigue funcionando como antes
- Sin gNMI: Switches siguen con SNMP
- MIBs online: Si local no existe, cae a descarga online (actual)
Archivos Nuevos Estimados
| Archivo | Fase | Lineas |
|---|---|---|
terminal/agent/syslog_receiver.py | 2 | ~80 |
terminal/agent/trap_receiver.py | 2 | ~100 |
terminal/agent/gnmi_subscriber.py | 3 | ~200 |
terminal/agent/rest_poller.py | 4 | ~100 |
monitoring/consumers.py (wireless WS) | 1 | ~100 |
network/management/commands/build_vendor_mibs.py | 5 | ~80 |
| Total nuevos | ~660 |
Archivos Modificados
| Archivo | Fase | Cambios |
|---|---|---|
terminal/agent/sentinel_scheduler.py | 1 | +fast_snmp_loop |
terminal/agent/local_agent.py | 1-4 | +syslog/trap/gnmi init |
network/services/mib_manager.py | 1 | +local-first fallback |
monitoring/api.py | 2 | +events endpoint |
network/models.py | 3-4 | +monitoring_protocols, gnmi_config |
static/js/pages/wireless/WirelessDetail.js | 1 | +WS listener |
Dockerfile | 1 | +MIB build stage |
config/urls.py | 1 | +WS route wireless |
build_agent.bat | 3 | +pygnmi/grpcio |
Metricas de Exito
| Metrica | Actual | Fase 1 | Fase 2 | Fase 3 |
|---|---|---|---|---|
| Latencia device→browser (metricas) | 60-90s | 15-30s | 15-30s | 1-10s (gNMI) |
| Latencia device→browser (eventos) | N/A | N/A | <1s | <1s |
| MIB cold start | 10-30s | 0s (standard) | 0s | 0s |
| Dependencia internet (MIBs) | 100% | 20% | 20% | 20% |
| Protocolos soportados | 1 (SNMP) | 1 | 3 (SNMP+Syslog+Trap) | 5 (+gNMI+REST) |
Nota: Xirrus XMS-E y cnMaestro utilizan WebSocket internamente para su gestion en tiempo real. Cuando el Agent pueda actuar como intermediario WebSocket (suscribiendose a las APIs de estos gestores cloud), la latencia para APs WiFi podra bajar a <1s tambien para metricas, no solo eventos. Esto se puede explorar como extension de la Fase 3 o como Fase independiente, dependiendo de la documentacion de las APIs WS de XMS-E y cnMaestro.
Creado: 21-02-2026 Autor: Claude + Edu
Véase también
- [[crearack-tech—backend—network-observatory]] — Network Observatory en backend
- [[crearack-tech—admin—monitoring-tools]] — herramientas admin de monitorización
- [[crearack-tech—architecture—saas-metrics-architecture]] — arquitectura de métricas SaaS
- [[crearack—monitoring—dashboards]] — dashboards de monitorización
- [[entity—monitoring—model—monitoringtarget]] — modelo MonitoringTarget