Saltar a contenido

Diagrama de Servicios

Arquitectura Completa

graph TB
    subgraph Usuarios["Usuarios"]
        U1["Usuario Municipal<br/>(Navegador)"]
        U2["Administrador<br/>(Navegador)"]
        U3["IA Externa<br/>(Claude, ChatGPT, Gemini)"]
    end

    subgraph Frontends["Frontends"]
        FE["GDI-FRONTEND<br/>Next.js 15 :3003"]
        BO["GDI-BackOffice-Front<br/>Next.js 15 :3013"]
    end

    subgraph Backends["Backends"]
        BE["GDI-Backend<br/>FastAPI :8000"]
        BOBE["GDI-BackOffice-Back<br/>FastAPI :8010"]
        MCP["GDI-MCP Server<br/>FastAPI :8005<br/>(integrado en Backend)"]
    end

    subgraph Microservicios["Microservicios"]
        PDF["GDI-PDFComposer<br/>FastAPI :8002"]
        NOT["GDI-Notary<br/>FastAPI :8001"]
        AGENT["GDI-AgenteLANG<br/>FastAPI :8004"]
    end

    subgraph Storage["Almacenamiento"]
        PG["PostgreSQL 17<br/>+ pgvector"]
        R2["Cloudflare R2<br/>(S3-compatible)"]
    end

    subgraph Auth["Autenticacion"]
        A0["Auth0<br/>(OAuth 2.0 / JWT)"]
    end

    subgraph AI["Proveedores IA"]
        OR["OpenRouter<br/>(Gemini Flash, Llama 3.3)"]
    end

    U1 --> FE
    U2 --> BO
    U3 --> MCP

    FE -->|"REST + Auth0 JWT"| BE
    BO -->|"REST + Auth0 JWT"| BOBE

    BE -->|"REST + API Key"| PDF
    BE -->|"REST + API Key"| NOT
    BE -->|"S3 API"| R2
    BE --> PG

    BOBE --> PG
    BOBE -->|"S3 API"| R2

    MCP -->|"OAuth 2.0"| A0

    AGENT -->|"REST + JWT"| BE
    AGENT --> PG
    AGENT -->|"API"| OR

    FE -->|"OAuth 2.0"| A0
    BO -->|"OAuth 2.0"| A0

Diagrama por Capas

graph LR
    subgraph Presentacion["Capa de Presentacion"]
        F1["GDI-FRONTEND :3003"]
        F2["GDI-BackOffice-Front :3013"]
    end

    subgraph Aplicacion["Capa de Aplicacion"]
        B1["GDI-Backend :8000"]
        B2["GDI-BackOffice-Back :8010"]
        B3["GDI-MCP Server :8005"]
    end

    subgraph Servicios["Capa de Microservicios"]
        S1["GDI-PDFComposer :8002"]
        S2["GDI-Notary :8001"]
        S4["GDI-AgenteLANG :8004"]
    end

    subgraph Datos["Capa de Datos"]
        D1["PostgreSQL + pgvector"]
        D2["Cloudflare R2"]
    end

    Presentacion --> Aplicacion
    Aplicacion --> Servicios
    Aplicacion --> Datos
    Servicios --> Datos

Puertos y Tecnologias

Servicio Puerto Tecnologia Workers Protocolo
GDI-FRONTEND 3003 Next.js 15 (Pages Router) Node.js HTTP
GDI-BackOffice-Front 3013 Next.js 15 (Pages Router) Node.js HTTP
GDI-Backend 8000 FastAPI + Gunicorn 8 Uvicorn workers HTTP
GDI-BackOffice-Back 8010 FastAPI + Uvicorn 1 worker HTTP
GDI-MCP Server 8005 FastAPI (integrado en Backend) Compartido MCP + HTTP
GDI-AgenteLANG 8004 FastAPI + Uvicorn 1 + AIWorker background HTTP
GDI-PDFComposer 8002 FastAPI + Gunicorn 4 Uvicorn workers HTTP
GDI-Notary 8001 FastAPI + Gunicorn 3 Uvicorn workers HTTP
PostgreSQL 5432 PostgreSQL 17 + pgvector Docker managed TCP

Dependencias entre Servicios

graph TD
    FE["GDI-FRONTEND"] --> BE["GDI-Backend"]
    BO["GDI-BackOffice-Front"] --> BOBE["GDI-BackOffice-Back"]

    BE --> PDF["GDI-PDFComposer"]
    BE --> NOT["GDI-Notary"]
    BE --> R2["Cloudflare R2"]
    BE --> PG["PostgreSQL"]

    BOBE --> PG
    BOBE --> R2

    AGENT["GDI-AgenteLANG"] --> BE
    AGENT --> PG
    AGENT --> OR["OpenRouter"]

    MCP["GDI-MCP Server"] --> PG
    MCP --> A0["Auth0"]

    FE --> A0
    BO --> A0

MCP Server integrado

El MCP Server (puerto 8005) esta integrado dentro del repositorio GDI-Backend en la carpeta api_gateway/. No es un servicio separado, sino un modulo del Backend que escucha en un puerto adicional.


Security Hardening

Medidas de seguridad implementadas transversalmente en los servicios.

XSS Prevention

Capa Libreria Uso
Backend (Python) nh3 Sanitizacion de HTML en save_document y contenido generado por usuarios
Frontend (JS) DOMPurify Sanitizacion de HTML antes de renderizar en el navegador

El backend sanitiza todo contenido HTML antes de persistirlo en la base de datos, eliminando tags y atributos peligrosos (scripts, event handlers, iframes, etc.). El frontend aplica una segunda capa de sanitizacion al renderizar contenido que proviene de la API.

Rate Limiting

El Gateway implementa rate limiting dual:

Mecanismo Tipo Limite Ventana
In-memory Sliding window por IP 60 requests 1 minuto
Redis Distribuido (Upstash) Configurable Configurable

Implementado en api_gateway/rate_limiter.py. Usa InMemoryRateLimiter con sliding window. La IP del cliente se extrae considerando proxies de Fly.io (fly-client-ip, x-forwarded-for).

Cuando se excede el limite, el servidor responde con 429 Too Many Requests e incluye el header Retry-After con los segundos de espera.

Permission Enforcement en MCP Tools

Las tools MCP verifican permisos del usuario autenticado antes de ejecutar cualquier operacion. El MCPContext incluye user_id y schema_name, que se propagan a los servicios de negocio para validar acceso a nivel de sector.

Sanitizacion de Datos Sensibles

Funcion Ubicacion Proposito
strip_storage_urls api_gateway/tools/_sanitize.py Remueve URLs de storage (R2) de las respuestas MCP
search_users Tools MCP Reduce datos privados en resultados de busqueda de usuarios

Las respuestas del Gateway nunca exponen URLs directas de Cloudflare R2 (pdf_url, signed_pdf_url). Estos campos se eliminan recursivamente antes de devolver datos al cliente MCP.