Repositorio de práctica orientado a demostrar experiencia con el SIMOVI Stack: un conjunto de tecnologías de uso habitual en sistemas de movilidad, transporte y backend distribuido.
Cada laboratorio agrupa tecnologías que se complementan naturalmente y produce un mini-proyecto funcional dentro de un dominio unificado: transporte público. Los datos y conceptos (rutas, paradas, vehículos, alertas) fluyen de un lab al siguiente, lo que permite apreciar la cohesión del stack completo.
| Capa | Tecnologías |
|---|---|
| Lenguaje / Runtime | Python, TypeScript, Rust |
| Backend | Django, Django REST Framework, Celery, Django Channels |
| Base de datos | PostgreSQL + PostGIS, TimescaleDB, Redis |
| Mensajería | RabbitMQ, MQTT (NanoMQ) |
| Data pipeline | Prefect, Polars, Parquet, GTFS |
| Data science | NumPy, SciPy, scikit-learn, Matplotlib |
| API alternativa | Strawberry (GraphQL) |
| CMS | Strapi |
| Frontend | Vue 3, Nuxt 3, Nuxt UI, TypeScript |
| Mobile | Capacitor, Ionic |
| TUI | Textual |
| Observabilidad | Prometheus, Grafana, OpenTelemetry |
| Semántica / MCP | Apache Jena/Fuseki, SPARQL, FastMCP |
| Seguridad | Zabbix, Wazuh |
| Infraestructura | Docker, Docker Compose, uv, pnpm |
fullstack-systems-lab/
├── docker_ctl.py # Utilidad de control del entorno (ver abajo)
│
├── lab-01-fundamentos/ # Python · PostgreSQL · Docker · uv · pytest · Textual
├── lab-02-django-api/ # Django · DRF · JWT · PostGIS · pytest-django · factory_boy
├── lab-03-async-realtime/ # Celery · RabbitMQ · Redis · Django Channels
├── lab-04-data-pipeline/ # Prefect · TimescaleDB · Polars · GTFS · NumPy · SciPy · scikit-learn · Matplotlib
├── lab-05-graphql-cache/ # Strawberry GraphQL · Redis · DataLoaders
├── lab-06-frontend-nuxt/ # Nuxt 3 · Vue 3 · TypeScript · Nuxt UI · Leaflet
├── lab-07-observability/ # Prometheus · Grafana · OpenTelemetry
├── lab-08-semantic-mcp/ # Fuseki · SPARQL · FastMCP · MQTT
├── lab-09-mobile/ # Capacitor · Ionic
├── lab-10-security-monitoring/ # Zabbix · Wazuh
├── lab-11-rust-ingestor/ # Rust · MQTT · Redis (microservicio de telemetría)
└── lab-12-strapi-cms/ # Strapi · PostgreSQL · Nuxt (integración frontend)
Cada laboratorio contiene su propio docker-compose.yml, README.md con instrucciones de ejecución, y es ejecutable de forma independiente.
Script en la raíz del repositorio que gestiona el ciclo de vida del entorno de desarrollo en Windows + Docker Desktop + WSL2.
python docker_ctl.pyPresenta un menú interactivo con dos operaciones:
| Opción | Acción |
|---|---|
| 1 — Iniciar | Detecta y lanza Docker Desktop si no está activo, espera hasta que el daemon esté listo y muestra los contenedores en ejecución. |
| 2 — Apagar | Detiene todos los contenedores activos, cierra Docker Desktop y ejecuta wsl --shutdown para liberar la RAM del proceso vmmem. |
Después de iniciar el entorno, cada laboratorio se levanta de forma independiente desde su propio directorio:
cd lab-XX-nombre
docker compose up -dLos únicos requisitos en el host son Docker Desktop y Python (para ejecutar docker_ctl.py). Todas las demás dependencias de cada laboratorio (intérpretes, bases de datos, brokers, herramientas) se resuelven íntegramente dentro de contenedores.
Los laboratorios siguen una progresión acumulativa:
Lab 01 (Fundamentos) ──→ Lab 02 (Django API) ──→ Lab 03 (Async/Realtime)
│ │
▼ ▼
Lab 05 (GraphQL) Lab 04 (Data Pipeline)
│ │
└──────┬────────────────┘
▼
Lab 06 (Frontend Nuxt)
│
┌──────┴───────┬──────────────┐
▼ ▼ ▼
Lab 07 (Observ.) Lab 09 (Mobile) Lab 12 (Strapi)
│
▼
Lab 08 (Semantic/MCP)
│ │
▼ ▼
Lab 10 (Security) Lab 11 (Rust)
Script que lee un CSV de paradas de bus, lo carga en PostgreSQL, lo exporta como Parquet con Polars, y cuenta con tests con pytest. Incluye un dashboard TUI con Textual para inspección de datos desde la terminal. Introduce el uso de uv como gestor de entornos Python.
API REST de rutas de transporte público con CRUD de rutas, paradas y horarios. Incluye autenticación JWT, permisos custom, queries geoespaciales con PostGIS (paradas cercanas, rutas por zona) y cobertura de tests con pytest-django y factory_boy.
Sistema de alertas de transporte. Celery procesa alertas en background con RabbitMQ como broker; Django Channels las distribuye por WebSocket con Redis como channel layer.
Pipeline ETL orquestado con Prefect que descarga datos GTFS, los transforma con Polars y los carga en TimescaleDB como series temporales. Incluye análisis estadístico con NumPy/SciPy, visualizaciones con Matplotlib, y modelos predictivos de demanda con scikit-learn en notebooks exploratorios.
Endpoint GraphQL sobre Django para consultar rutas, paradas y horarios. Implementa DataLoaders para resolver el problema N+1 y caching en Redis.
Dashboard de transporte con mapa interactivo (Leaflet), tabla de rutas que consume la API DRF, y feed en tiempo real vía WebSocket. Incluye composables tipados y server routes de Nuxt como BFF.
Stack de monitoreo que instrumenta el Django API del Lab 02. Expone métricas HTTP con django-prometheus, traces con OpenTelemetry SDK, y un dashboard Grafana preconfigurado.
Ontología de transporte en RDF/Turtle consultable vía SPARQL en Fuseki. Servidor MCP (FastMCP) que expone herramientas sobre la ontología. Simulación de sensores GPS con MQTT sobre NanoMQ.
Versión mobile del dashboard del Lab 06 empaquetada como aplicación nativa Android con Capacitor. Incluye acceso a GPS nativo del dispositivo.
Monitoreo de infraestructura con Zabbix y detección de intrusiones con Wazuh sobre los contenedores del stack.
Microservicio de alta frecuencia escrito en Rust que consume posiciones GPS de vehículos desde MQTT (NanoMQ), las valida y las publica en Redis. Introduce el modelo de ownership, tipos seguros y concurrencia sin data races. Diseñado como el componente de ingesta de telemetría que alimenta el pipeline del Lab 04.
CMS headless con Strapi para gestionar contenido dinámico del sistema de información de transporte (alertas editoriales, avisos de servicio, documentación de rutas). Incluye integración con el frontend Nuxt del Lab 06 como fuente de contenido adicional al API DRF.
| # | Tecnología | Lab |
|---|---|---|
| 1 | Python | 01 |
| 2 | PostgreSQL | 01, 02 |
| 3 | PostGIS | 02 |
| 4 | Docker / Docker Compose | Todos |
| 5 | uv (entornos Python) | 01–05, 07–08 |
| 6 | pnpm (entornos JS) | 06, 09, 12 |
| 7 | Django | 02, 03, 05, 07 |
| 8 | Django REST Framework | 02 |
| 9 | JWT Auth / Permisos | 02 |
| 10 | pytest / testing | 01, 02, 03, 05 |
| 11 | Celery | 03 |
| 12 | RabbitMQ | 03 |
| 13 | Redis | 03, 05, 11 |
| 14 | Django Channels / WebSockets | 03 |
| 15 | GTFS / ETL | 04 |
| 16 | Prefect | 04 |
| 17 | TimescaleDB | 04 |
| 18 | Polars / Parquet | 01, 04 |
| 19 | NumPy | 04 |
| 20 | SciPy | 04 |
| 21 | scikit-learn | 04 |
| 22 | Matplotlib | 04 |
| 23 | Strawberry (GraphQL) | 05 |
| 24 | TypeScript | 06 |
| 25 | Vue 3 | 06 |
| 26 | Nuxt 3 | 06, 12 |
| 27 | Nuxt UI | 06 |
| 28 | Textual (TUI) | 01 |
| 29 | Prometheus | 07 |
| 30 | Grafana | 07 |
| 31 | OpenTelemetry | 07 |
| 32 | Apache Jena / Fuseki (SPARQL) | 08 |
| 33 | FastMCP | 08 |
| 34 | MQTT / NanoMQ | 08, 11 |
| 35 | Capacitor / Ionic | 09 |
| 36 | Zabbix | 10 |
| 37 | Wazuh | 10 |
| 38 | Rust | 11 |
| 39 | Strapi | 12 |