Descripción general

Se ha identificado una vulnerabilidad en Langflow que permite a usuarios no autenticados subir cantidades arbitrarias de datos al servidor sin ningún tipo de restricción. El único requisito para explotar esta vulnerabilidad es tener acceso de red al servicio Langflow. No se requiere conocimiento previo ni credenciales.

Esta vulnerabilidad puede derivar en dos impactos distintos: agotamiento del espacio en disco del servidor, lo que puede provocar una condición de DoS, y filtración de información sensible mediante la exposición de la ruta absoluta del directorio de caché de Langflow en el servidor.

Detalles técnicos

El problema reside en el endpoint POST /api/v1/upload/{flow_id}, definido en langflow/api/v1/endpoints.py. Dicho endpoint carece por completo de mecanismo de autenticación y no valida el parámetro flow_id, a diferencia de otros endpoints de la aplicación.

python
@router.post(
    "/upload/{flow_id}",
    status_code=HTTPStatus.CREATED,
    deprecated=True,
)
async def create_upload_file(
    file: UploadFile,
    flow_id: UUID,
) -> UploadFileResponse:
    ...

La función save_uploaded_file persiste el archivo directamente en el sistema de archivos local sin aplicar ningún límite de tamaño ni validación de contenido. Adicionalmente, la respuesta devuelve la ruta absoluta del archivo almacenado, lo que constituye una filtración de información que puede ser aprovechada para encadenar otros vectores de ataque.

Prueba de concepto

Cualquier atacante con acceso de red puede ejecutar el siguiente comando para subir un archivo arbitrario al servidor:

bash
curl 'http://localhost:7860/api/v1/upload/<any_uuid>' -F "file=@<any_file>"

Ejemplo real de explotación y respuesta del servidor:

bash
curl 'http://localhost:7860/api/v1/upload/11111111-1111-1111-1111-111111111111' -F "file=@/tmp/dummy.txt"

Respuesta obtenida:

json
{
  "flowId": "11111111-1111-1111-1111-111111111111",
  "file_path": "/Users/ori/Library/Caches/langflow/11111111-1111-1111-1111-111111111111/9d63c3b5b7623d1fa3dc7fd1547313b9546c6d0fbbb6773a420613b7a17995c8.txt"
}

Como se observa, la respuesta expone la ruta absoluta del directorio de caché de Langflow en el servidor, información que puede ser utilizada para preparar ataques adicionales.

Impacto

  1. Agotamiento de espacio en disco: un atacante puede subir volúmenes masivos de datos de forma repetida hasta saturar el almacenamiento del servidor, provocando una condición de DoS que afecta a todos los usuarios y servicios que dependan de dicho servidor.

  2. Filtración de información: la respuesta del endpoint revela la ruta absoluta del directorio de caché de Langflow, lo que permite al atacante conocer la estructura interna del sistema de archivos del servidor y utilizar esa información para encadenar otras primitivas de ataque.

Corrección recomendada

Los investigadores propusieron las siguientes medidas de mitigación:

  1. Añadir autenticación obligatoria al endpoint de subida de archivos.
  2. Devolver únicamente la ruta relativa o el nombre del archivo en la respuesta, nunca la ruta absoluta.

Parche oficial

La vulnerabilidad fue corregida en la versión 1.9.1 mediante el PR #12831. El endpoint deprecado POST /api/v1/upload/{flow_id} incorpora ahora la dependencia get_flow, que exige un usuario autenticado y la propiedad del flujo correspondiente. Los flujos inexistentes o pertenecientes a otro usuario devuelven un error 404. Además, se aplica el límite configurado mediante max_file_size_upload, retornando HTTP 413 cuando se supera dicho límite, cerrando así los vectores de subida no autenticada y agotamiento de disco.

Nota: tras la aplicación del parche, la respuesta continúa devolviendo la ruta absoluta del archivo mediante el campo file_path, si bien ahora esta información únicamente se expone al propietario autenticado del flujo.

Se recomienda actualizar a Langflow 1.9.1 o superior de forma inmediata.

Créditos

Vulnerabilidad descubierta y reportada por Ori Lahav, investigador de seguridad en Rubrik Inc. Verificada sobre el commit 2d67402b1dbaefcbce85a244d4a6cd5e4bda1cfe.