
🌐 También en: English · Deutsch · Français
Hace unos días, las noticias nos sirvieron una historia deliciosamente inquietante: OpenAI admitió que dos de sus modelos de IA, durante una evaluación de seguridad, llegaron de verdad a escapar de su sandbox de pruebas, se pasearon por el Internet abierto y vulneraron la infraestructura de producción de Hugging Face —encadenando un zero-day real— solo para robar las respuestas de un benchmark 🤖💥 (Malwarebytes, The Hacker News). Esa historia es la versión de pesadilla. Lo que hice yo es justo lo contrario, aburrido y sano: cogí una IA y la apunté a mi propio blog —con permiso, a propósito, sin ir a ningún sitio al que no estuviera invitada— solo para ver si mis propias defensas aguantan de verdad. El mismo tipo de tecnología, pero dirigida hacia dentro, a algo que es mío, no hacia fuera, a los servidores de otra persona. Nada se escapó de ningún sitio. 🪞 Un aviso rápido antes de que alguien se escandalice: este blog es mío. Autorizar un escaneo de seguridad es cosa de un comité de una sola persona, y el comité votó que sí. ✅ Ningún sandbox sufrió daños, nada se escapó, y la única infraestructura en riesgo era la mía. Después de toda la saga de wp2shell tenía curiosidad de todas formas: mi blog funciona sobre un stack K3s + WordPress hecho a mano que yo mismo bastiono —con, para ser totalmente transparente, una IA de copiloto tanto para el bastionado como para esta misma evaluación. Así que, ¿cómo aguantaría si alguien lo pinchara a propósito? Solo hay una forma de averiguarlo y ver qué se cae.🎩 Un pequeño desvío: sombreros blancos, grises y negros
Como no todos los que leen esto viven en el mundo de la seguridad: la palabra «hacker» viene en colores, y estos importan:- 🤍 White hat: los buenos. Prueban sistemas con permiso para encontrar y tapar agujeros antes de que lo hagan los malos. Piensa en un inspector de seguridad contra incendios.
- 🖤 Black hat: los delincuentes de verdad. Entran sin permiso, por dinero o para causar daño. La historia de los modelos de OpenAI vulnerando Hugging Face de arriba es, básicamente, un black hat accidental.
- 🩶 Gray hat: el término medio. Husmea en la zona difusa —normalmente sin mala intención, pero tampoco siempre limpiamente dentro de las líneas.
🚫 Ronda 1: el servidor banea a su propio dueño
Empecé como empieza cualquier atacante aburrido: un escaneo de puertos rápido para ver qué está escuchando. Conexiones rápidas a un puñado de puertos. Milisegundos después —todos y cada uno de los puertos se apagaron. HTTP, HTTPS, incluso mi propio acceso SSH de administración. El cortafuegos había visto la ráfaga de conexiones, decidido «eso es un escáner» y metido toda mi IP en una lista de bloqueo. 🧱 Luego, más tarde, sin dejar de husmear, pedí un par de las rutas clásicas de «¿hay alguna copia de seguridad olvidada por ahí?». A la segunda petición, la capa de detección de intrusiones dijo «sondeo de rutas maliciosas conocidas, hasta aquí hemos llegado» y me plantó un baneo de 24 horas. 🔨 Tuve que desbanearme a mí mismo a través de la consola del proveedor, como un cerrajero que se ha dejado las llaves dentro del coche. Esto es exactamente lo que quieres. Un atacante no se encuentra con un objetivo paciente e indulgente: tiene un puñado de peticiones antes de que toda la IP acabe en un agujero negro. Las cuentas le salen fatal: quemar una IP, no aprender casi nada, volver a intentarlo desde otra nueva, que lo vuelvan a banear. 🔁 No es un muro, es un muro que muerde.✅ El marcador: todo lo que le lancé
Una vez que (a regañadientes) me puse a mí mismo en la lista blanca para poder terminar de probar la capa de aplicación, esta es la checklist que seguí: las cosas aburridas que deciden en silencio si un sitio es un objetivo fácil o no:- 🔒 TLS: solo 1.2 y 1.3, cifrado moderno, protocolos antiguos rechazados. ✔️
- 🧾 Cabeceras de seguridad: HSTS con preload, protección contra clickjacking, MIME-sniffing desactivado, referrer y permissions bien cerrados. ✔️
- 🕵️ Fingerprinting del servidor: ni versión del servidor web ni versión de PHP filtrándose en las cabeceras. ✔️
- 👤 Enumeración de nombres de usuario (el clásico primer paso antes de una juerga de adivinar contraseñas): bloqueada por todas las vías que probé: el viejo truco de la query, la API REST, todo. ✔️
- 📡 xmlrpc (el amplificador que los bots adoran para la fuerza bruta): cerrado, tanto GET como POST. ✔️
- 🗂️ Archivos sensibles (config, dotfiles, metadatos de VCS, la lista de la compra de siempre): denegados. ✔️
- 📁 Listado de directorios: desactivado. No hay nada que curiosear. ✔️
- 🔑 Los endpoints sensibles de la API REST: todos los que importaban respondieron con un seco «no tienes permiso para hacer eso». ✔️
😰 El que me puso nervioso (y al final no)
Todo sitio WordPress tiene su habitación más terrorífica, y aquí era el plugin de migración/copias de seguridad. Esos chismes pueden, en principio, entregar un archivo completo del sitio —base de datos, config, secretos, el diario entero— si la puerta no está cerrada. Así que sacudí esa puerta en concreto. 🚪 Estaba cerrada. Todas las acciones sensibles respondían «no autorizado» sin haber iniciado sesión, y el propio plugin estaba en su versión actual, sin ningún bypass conocido. Ese era el resultado que de verdad me importaba, y salió limpio. 🎯 La lección para cualquiera que tenga un WordPress: el plugin que puede exportar todo tu sitio es el que hay que revisar primero, no el último.🔧 Lo que encontré, y arreglé esa misma noche
Ningún pentest sale impecable, y el mío tampoco, pero lo que quedó era el equivalente en seguridad a «te has dejado una ventana sin pestillo en el tercer piso, detrás de una verja cerrada con llave». Cosas de cinturón y tirantes:- 📄 Algunos números de versión de componentes se podían leer en sitios donde no hacía falta. Revelar versiones solo ayuda a un atacante si vas atrasado con los parches; este stack se actualiza y se reinicia solo, así que es más bien una cuestión de orden. Aun así, lo cerré.
- 💾 La regla que bloquea los archivos de copia de seguridad perdidos de los editores no cubría un par de sufijos (los que deja tu editor de terminal). No había nada realmente expuesto, pero «hoy no había nada expuesto» no es un control de seguridad, así que amplié la red. Ahora cualquier cosa que parezca un archivo olvidado recibe un rechazo rotundo.
- 📊 El único «vaya, bien visto» de verdad del día: mi panel de monitorización siempre ha estado detrás de un usuario + contraseña en condiciones, pero era el único inicio de sesión de toda la máquina sin bloqueo automático contra fuerza bruta, a diferencia del inicio de sesión del blog, que banea al instante a quien adivina una y otra vez. Así que le di al panel el mismo trato: unos cuantos inicios de sesión fallidos seguidos y a toda la IP se le enseña la puerta. Contraseña y portero ahora, no solo la contraseña. 🚪👮




