Justo después de php2shell ha llegado node2shell, un fallo en el descompresor Brotli que trae Node.js y que puede acabar en ejecución remota de código. Salió en las actualizaciones de seguridad de Node.js del 21 de octubre, el mismo día que los parches de PHP.
Aviso: no he probado el exploit ni lo he reproducido. Esto es lo que cuentan las fuentes que enlazo abajo y lo que haría yo con ello.
Qué ha pasado
El fallo es CVE-2026-111497, una escritura fuera de límites en el decodificador Brotli. Si le llegan datos comprimidos mal formados, escribe más allá del buffer que tiene reservado. Node.js lo puntúa como High y describe el impacto como ejecución remota de código.
Lo encontró Codex Security de OpenAI (Khai Tran y Sylvie Mayer). El arreglo en sí no es nuevo: es un commit de Brotli de febrero de 2026 que Node.js ha incorporado ahora a su copia de la librería.
Venía en un paquete de 10 CVE, 4 de ellas High. Las otras tres High tocan la comprobación del nombre de host en TLS y dns.resolve con caracteres NUL, así que también merece la pena actualizar por ellas.
A quién afecta
No basta con usar Node.js: hace falta que tu aplicación descomprima Brotli que controla otra persona. Los casos que señalan las fuentes:
Express 5 y body-parser 2.x: descomprimen el cuerpo de las peticiones que llegan con Content-Encoding: br, así que cualquier cliente puede mandar uno. Un servidor HTTP de Node.js sin nada encima no lo hace por defecto.
fetch(): descomprime solo las respuestas Brotli. Si tu aplicación pide cosas a servidores que no controlas (webhooks, URLs que mete el usuario), el ataque puede venir por ahí.
node:zlib: si pasas datos que no son tuyos a brotliDecompress o createBrotliDecompress. Muchos frameworks lo hacen por dentro.
Las versiones corregidas:
Node.js 26.12.1, 24.22.1 y 22.23.4
25.x, 23.x, 20.x y anteriores son EOL y no van a recibir parche
Bun también estaba afectado, se arregla en la 1.4.4
Cómo de explotable es
Aquí las fuentes no coinciden del todo. Ron Masas, de Imperva, dice que lo han reproducido como ejecución remota sin autenticar y que con un app.use(express.json()) en un runtime vulnerable basta. Aikido cuenta que se consiguió ejecutar código contra la imagen oficial de Node.js 24.22.0 en Linux arm64, pero no a la primera. Otros análisis solo consiguen tumbar el proceso y lo dejan en denegación de servicio.
Hay varios PoC en GitHub y la mayoría lo que hacen es crashear Node.js sin parche. A 22 de octubre nadie había visto explotación real y no está en el catálogo KEV de CISA. Igual que con php2shell, yo no me fiaría de ningún PoC, ni para probarlo ni para descartar que estés expuesto.
Qué haría
Actualizar el runtime, que es lo único que lo arregla. Node.js no da ningún workaround. Mientras tanto, rechazar las peticiones con Content-Encoding: br en el proxy, el balanceador o un middleware corta la entrada por peticiones, pero no cubre las respuestas que tu aplicación descarga con fetch().
Para ver qué tienes:
terminal
# versión del runtime en el host o en el runner de CInode --version# versión dentro de una imagen$ docker run --rm <imagen> node --version# si usas Express 5 o body-parser 2.xnpm ls express body-parser# código propio que descomprime Brotli$ grep -rn "brotliDecompress\|createBrotliDecompress" --include=*.js --include=*.ts .
Ojo con las imágenes fijadas a una versión. Un Dockerfile con FROM node:24.22.0 sigue siendo vulnerable por muchas veces que lo reconstruyas; hay que subir la etiqueta. Y si usas el Node.js de tu distribución, puede que tire de la librería Brotli del sistema, así que mira también el aviso de tu distro.