Guías de seguridad
Código escrito por IA filtró una clave de API y generó cargos fraudulentos — la causa real era un CVSS 10.0 sin parchear
Una app creada con ayuda de IA tiene su clave de API robada y acumula cargos fraudulentos. La causa real no era la clave en sí, sino un RCE público CVSS 10.0 sin parchear. Qué pasó y cómo evitar que se repita, contado de forma defensiva.
Un caso que los desarrolladores indie poco familiarizados con la seguridad sufren con frecuencia, con todo detalle identificable eliminado y convertido en lección. Aquí no hay reproducción del ataque — el objetivo es la defensa, para que el mismo error no te ocurra a ti.
- Clase
- Fuga de clave de API / facturación fraudulenta
- Gravedad
- Crítica (un CVSS 10.0 publicado abusado)
- Causa raíz
- Un RCE preautenticación en el framework web dejado sin parchear durante meses
- Alcance de la fuga
- Todos los secretos del entorno (todo el llavero)
- Alcance de la ejecución
- Quedó dentro de un contenedor sin privilegios (root del host intacto)
- Corrección permanente
- ①actualizar a la versión parcheada ②rotar todas las claves ③monitoreo automático de CVE
«Detuve los cargos» ≠ «resuelto»
Detener la factura es primeros auxilios. Cerrar la vía de fuga es una operación aparte. Solo terminaste cuando hiciste ambas.
Qué pasó (línea de tiempo)
Día 0 — desplegado y en marcha
Una app construida con ayuda de IA se desplegó y corría en producción.Un día — la factura se dispara
La factura de IA en la nube salta de repente. Trabajos masivos en un modelo que jamás se usaría, haciendo tareas que no eran suyas.Investigación — abuso de terceros
«Nuestra app se descontroló» no lo explica. Un tercero la ejecutaba con una clave robada.La caza — empieza la investigación real
«¿De dónde se filtró la clave?» — esa fue la investigación real.
Por qué no se detectó al principio (los rodeos)
En el orden en que se cometieron los errores — porque los errores son la lección.
Saltar a un culpable
→ Antes de decidir «culpa mía» o «culpa de ellos», mira primero los datos.
Un grep limpio casi trajo alivio
Ocultar el síntoma pareció una solución
Un grep limpio no es el visto bueno
Aunque no haya ninguna clave en ningún archivo, una vulnerabilidad puede extraer variables de entorno de un proceso en ejecución. Las fugas ocurren en tiempo de ejecución (RCE, cabeceras HTTP), no solo en archivos. Véase qué es un RCE.
La causa real: un CVSS 10.0 publicado y descuidado
Una firma extraña en registros de acceso antiguos coincidió con la inteligencia de amenazas al instante. El rango de versiones del framework web en uso tenía un RCE preautenticación publicado (CVSS 10.0) que ya estaba siendo explotado activamente — y había corrido sin parchear durante meses.
- No era un fallo pasivo — era un atacante ejecutando código en el servidor y exfiltrando el entorno.
- El salvavidas: la ejecución quedó dentro de un contenedor sin privilegios (no se tomó el root del host). La revisión de la brecha no encontró puerta trasera persistente, minero ni C2 — el impacto confirmado fue el robo de secretos.
- Como la base de datos interna era alcanzable, la respuesta asumió que el contenido de la BD también se había filtrado.
Lección: cuando algo se comporta de forma extraña, sospecha primero de un CVE conocido. No supongas que es un fallo tuyo.
El conteo también estaba mal — juzga por la versión en ejecución
Ampliando, se reportaron «8 dependencias vulnerables más» — también incorrecto. Se habían contado por el límite inferior en package.json (el rango con el caret ^). Las verdaderamente peligrosas eran solo las 2 dependencias fijadas que habían quedado atrás.
Comprueba tus propias versiones en ejecución
Mira las versiones realmente resueltas, en el lockfile o en el contenedor en ejecución.
# npm: ve lo que está realmente instalado
npm ls next react react-dom
# dentro de un contenedor en ejecución
docker exec <container> npm ls <package>Los números de aquí son la verdad — no el ^ de package.json.
Lo que se hizo primero (pasos reproducibles)
Revocar de inmediato la clave abusada
Actualizar el framework a la versión parcheada
Rotar todos los secretos
Revisión de la brecha
Defensa del lado de la cuenta
La prevención real: deja que las máquinas vigilen
Reducido a lo esencial, este incidente fue «un humano pasó por alto un CVSS 10.0 publicado». Las patrullas manuales siempre se pierden cosas. Las máquinas no.
Escaneo de dependencias que puedes empezar hoy
Gratis para empezar — un paso en CI.
# OSV scanner (Google) revisa tu lockfile
osv-scanner --lockfile=pnpm-lock.yaml
# En GitHub, activa Dependabot (Settings del repo → Security)Este sitio mismo, conforme a esta lección, monitorea sus propias dependencias en busca de CVE — practicamos lo que recomendamos.
Lecciones
Errores comunes
- Dar por terminado al «detener los cargos»
- Relajarse porque el grep está limpio
- Enmascarar el síntoma en un proxy y sentirlo resuelto
- Contar vulnerabilidades por el piso de
package.json - Rotar solo la única clave de la que se confirmó abuso
Defensa correcta
- Tratar los primeros auxilios y «cerrar la vía de fuga» como dos trabajos distintos, y hacer ambos
- Sospechar también de fugas en tiempo de ejecución (RCE, cabeceras)
- Actualizar la raíz (el framework)
- Juzgar por la versión realmente en ejecución
- Reemplazar todo el entorno si se filtra
En una línea: la factura descontrolada fue la punta del iceberg. La causa real fue un RCE CVSS 10.0 descuidado — y la verdad no vino de una corazonada con suerte, sino de equivocarse, chocar y pulir los errores.
Leer a continuación
- Glosario: qué es un RCE · qué es un CVE · qué es CVSS
- Defensa: ejecutar Next.js de forma segura (higiene de CVE)
- Incidente: cuando un .env quedó expuesto al mundo entero
FAQ
QSi se filtra una clave de API, ¿basta con revocar solo la clave que se abusó?
No. Cuando la vía de fuga está en tiempo de ejecución (un RCE o una fuga de cabeceras), asume que todos los secretos del entorno se filtraron a la vez y rótalos todos. La clave que viste abusada es solo la punta del iceberg.
QSi un grep en mi código y en git no encuentra claves, ¿estoy a salvo?
No necesariamente. Aunque no haya ninguna clave en ningún archivo, una vulnerabilidad del framework puede exfiltrar las variables de entorno directamente del proceso en ejecución. Las fugas también ocurren en tiempo de ejecución, no solo en archivos.
Q¿Qué impide de forma más fiable que esto vuelva a ocurrir?
Monitorear tus dependencias en busca de CVE con una máquina. La causa raíz aquí fue que un humano pasó por alto un CVSS 10.0 publicado durante meses; Dependabot u osv-scanner cierran esa brecha de forma estructural.