🚨
ACCIÓN INMEDIATA REQUERIDA — NO LANZAR A PRODUCCIÓN
Se han identificado 2 vulnerabilidades críticas que permiten acceso completo a la base de datos y suplantación de administradores. Requieren remediación antes del lanzamiento previsto para el 2026-07-01.
📊
Resumen Ejecutivo
Top 3 Hallazgos Prioritarios
1
SQL Injection en búsqueda de pacientes
Crítica
CVSS 9.8
Extracción masiva de BD + RCE
2
JWT con secreto hardcodeado débil
Crítica
CVSS 9.1
Forja de tokens admin
3
IDOR en expedientes clínicos
Alta
CVSS 8.1
Acceso a datos de 2.400 clínicas
Puntuación Global de Riesgo
8.7
/ 10.0 — Nivel CRÍTICO
0 — Ninguno
4 — Medio
7 — Alto
10 — Crítico
Impacto potencial RGPD
Registros expuestos
~50.000+
Tipo de datos
Categoría especial (Art.9)
Multa máxima estimada
4% facturación anual
Notificación AEPD
Obligatoria (Art.33)
Modalidad de prueba
Gray Box · OWASP Testing Guide v4.2 · PTES
Acceso: código fuente + credenciales de entorno de staging
🗺️
Cobertura OWASP Top 10 — Mapa de Hallazgos
A01:2021
Broken Access Control
1
A02:2021
Cryptographic Failures
1
A04:2021
Insecure Design
0
A05:2021
Security Misconfig
3
A06:2021
Vulnerable Components
1
A08:2021
Integrity Failures
0
A09:2021
Logging Failures
1
📋
Resumen de Hallazgos (10 total)
| # |
Severidad |
CVSS |
Hallazgo |
Categoría OWASP |
Prioridad |
| 01 |
Crítica |
|
SQL Injection en búsqueda de pacientes |
A03 – Injection |
P1 |
| 02 |
Crítica |
|
JWT firmado con secreto hardcodeado débil |
A02 – Crypto Failures |
P1 |
| 03 |
Alta |
|
IDOR en expedientes clínicos |
A01 – Broken Access Control |
P1 |
| 04 |
Alta |
|
Dependencias con CVEs activos (lodash, express-jwt) |
A06 – Vulnerable Components |
P2 |
| 05 |
Alta |
|
Stored XSS en notas de expediente clínico |
A03 – Injection |
P1 |
| 06 |
Media |
|
S3 bucket de pacientes accesible públicamente |
A05 – Security Misconfig |
P2 |
| 07 |
Media |
|
Sin rate limiting en endpoints de autenticación |
A07 – Auth Failures |
P2 |
| 08 |
Media |
|
Ausencia de cabeceras de seguridad HTTP |
A05 – Security Misconfig |
P2 |
| 09 |
Baja |
|
Secreto de API Stripe expuesto en logs |
A09 – Logging Failures |
P3 |
| 10 |
Baja |
|
Información de versión expuesta |
A05 – Security Misconfig |
P4 |
🔍
Hallazgos Detallados
📝 Descripción
El endpoint GET /api/v2/patients/search construye la consulta SQL concatenando directamente el parámetro q sin sanitizar. Cualquier usuario autenticado puede extraer toda la base de datos incluyendo historiales clínicos y credenciales de dietistas.
💥 Impacto
Acceso no autorizado a datos de salud de 2.400+ clínicas (categoría especial RGPD). Extracción masiva de credenciales. Posible RCE. Multa RGPD: hasta 4% del volumen anual.
🔬 Evidencia
GET /api/v2/patients/search?q=' UNION SELECT
username,password_hash,email,NULL,NULL
FROM users--
HTTP 200 OK
{"results": [{"name": "admin",
"email": "admin@nutritrack.pro",
"dob": "$2b$10$..."}]}
⚡ 2.847 registros extraídos en < 3 segundos
🔧 Remediación
Reemplazar concatenación con prepared statements. Implementar ORM (Prisma/TypeORM). Añadir WAF. Auditar TODOS los endpoints de búsqueda.
📝 Descripción
El secreto de firma JWT está hardcodeado en el repositorio como JWT_SECRET='nutritrack2023'. La clave es crackeada con hashcat en < 2 minutos. Un atacante puede forjar tokens con rol administrador sin credenciales.
💥 Impacto
Escalada de privilegios total. Cualquier usuario puede obtener acceso de administrador a todas las clínicas. Posibilidad de borrado masivo de datos.
🔬 Evidencia
# /src/config/auth.js (commit a4f8c21):
const JWT_SECRET = 'nutritrack2023';
# Forja de token admin en Python:
import jwt
token = jwt.encode(
{'sub': 'attacker',
'role': 'admin',
'exp': 9999999999},
'nutritrack2023', 'HS256'
)
# ✅ Acceso panel admin verificado
🔧 Remediación
Rotar secreto JWT inmediatamente. Mover a variable de entorno con 256+ bits de entropía. Migrar a RS256 (clave asimétrica). Invalidar todos los tokens activos.
📝 Descripción
Los endpoints de pacientes no verifican que el paciente pertenezca a la clínica del usuario autenticado. Con un ID válido (secuencial, fácil de enumerar), cualquier dietista puede acceder a expedientes de otras clínicas.
💥 Impacto
Filtración masiva de datos de salud (RGPD Art. 9). Cualquier dietista puede leer expedientes de las 2.400 clínicas. Riesgo de reidentificación y venta de datos.
🔬 Evidencia
# Autenticado como clinica-142:
GET /api/v2/patients/8847/records
Authorization: Bearer <token_clinica_142>
HTTP 200 OK — Paciente de clínica 391:
{"patient_id": 8847,
"clinic_id": 391,
"records": [{"date": "2026-05-01",
"weight": 78.3,
"diagnosis": "Síndrome metabólico"}]}
🔧 Remediación
Verificar patient.clinic_id === user.clinic_id en cada request. Usar UUIDs en lugar de IDs secuenciales. Añadir tests de autorización.
🎯
Matriz de Prioridad de Remediación
P1
SQL Injection en búsqueda de pacientes
Crítica
Esfuerzo: Medio
Plazo: INMEDIATO
P1
JWT con secreto hardcodeado
Crítica
Esfuerzo: Bajo
Plazo: HOY
P1
IDOR en expedientes clínicos
Alta
Esfuerzo: Medio
Plazo: 48 horas
P1
Stored XSS en notas clínicas
Alta
Esfuerzo: Bajo
Plazo: 48 horas
P2
Dependencias con CVEs (lodash, express-jwt)
Alta
Esfuerzo: Bajo
Plazo: Este sprint
P2
S3 bucket público de pacientes
Media
Esfuerzo: Bajo
Plazo: Este sprint
P2
Sin rate limiting en login
Media
Esfuerzo: Bajo
Plazo: Este sprint
P3
Secreto Stripe en logs
Baja
Esfuerzo: Bajo
Plazo: Este trimestre
Clave de prioridades:
P1 = Corregir inmediatamente (bloquea lanzamiento)
P2 = Corregir en este sprint
P3 = Este trimestre
P4 = Backlog
📈
Estadísticas del Pentest