Skip to content
KitploitKITPLOIT
HerramientasExploitsBlog
Log in
Enviar
HerramientasExploitsBlog
Enviar

¡Herramientas de Hacking, PenTest y Ciberseguridad para tu Arsenal de Seguridad!

Kitploit es un directorio de herramientas de hacking, ciberseguridad y pentesting. Descubre las últimas actualizaciones de proyectos para encontrar vulnerabilidades, analizar sistemas, automatizar pruebas y fortalecer tu seguridad.

··Feeds·Contacto·Privacidad·© 2026 Kitploit

Directorio de Herramientas

Categorías

Ver todas las categorías
Loading categories
CVE-2026-34213 — Un usuario de Docmost con pocos privilegios podría proporcionar un attachmentId de una víctima al endpoint de carga genérico y sobrescribir el adjunto almacenado de otra página dentro del mismo espacio de trabajo. | Kitploit
Herramientas/GitHubGitHub/0xmrma/cve-2026-34213
Análisis de VulnerabilidadesExplotación de Aplicaciones WebPruebas de PenetraciónPapers e InvestigaciónAprendizaje y Educación
GitHub0xmrma/cve-2026-34213

CVE-2026-34213

Un usuario de Docmost con pocos privilegios podría proporcionar un attachmentId de una víctima al endpoint de carga genérico y sobrescribir el adjunto almacenado de otra página dentro del mismo espacio de trabajo.

Ver Repositorio
53hace 3 mesesAún no revisado

Más Populares

Ver todos →

Descubre las herramientas más usadas por nuestra comunidad.

Explora todas las herramientas

Explora nuestra colección de herramientas

Ver todas las herramientas →
Compartir

CVE-2026-34213

Un usuario de Docmost con pocos privilegios podría proporcionar un attachmentId de una víctima al endpoint de carga genérico y sobrescribir el archivo adjunto de otra página dentro del mismo espacio de trabajo.

Introducción

Identifiqué, divulgué responsablemente y reproduje una falla de autorización de severidad Alta en Docmost, la plataforma de documentación colaborativa de código abierto.

El sitio oficial de Docmost la presenta como una wiki local preparada para empresas con más de 3 millones de descargas, y afirma que es utilizada por equipos en organizaciones como Vilnius City, Bechtle, el Gobierno Australiano, la Cruz Roja y ETS Quebec.

El error residía en la ruta genérica de carga de archivos que Docmost también utiliza para los flujos de guardado/actualización de diagramas.

Estaba revisando ese código con una pregunta muy específica en mente:

¿Qué sucede si el endpoint de carga verifica el acceso de edición en una página, pero el objetivo de sobrescritura se selecciona con un ID de adjunto separado controlado por el usuario?

En este caso, esa pregunta condujo directamente a una falla real de vinculación de objetos.

Docmost permitía que un llamador enviara:

  • un pageId de una página que tenía permiso para editar, y
  • un attachmentId perteneciente a una página diferente en el mismo espacio de trabajo

El servidor realizaba una comprobación de consistencia de sobrescritura, pero la guardia utilizaba la lógica booleana incorrecta.

Eso significaba que la solicitud podía pasar la autorización y sobrescribir el archivo adjunto de la víctima de todas formas.

Este problema se convirtió en CVE-2026-34213.

Docmost: docmost/docmost
Aviso de seguridad: GHSA-89fp-2hch-j9gp
CVE: CVE-2026-34213
Corregido en: v0.71.0

photo0 ---

Cadena de Ataque

pageId controlado por el atacante con acceso de edición -> attachmentId de la víctima controlado por el atacante -> guardia de sobrescritura defectuosa trata la sobrescritura entre páginas como válida -> ruta de almacenamiento reconstruida a partir del attachmentId de la víctima -> bytes del atacante reemplazan el archivo de la víctima -> la página de la víctima continúa sirviendo el archivo adjunto modificado


Qué Hace Esta Parte de Docmost

Docmost almacena los archivos adjuntos subidos a las páginas como registros en la base de datos más archivos de respaldo en almacenamiento.

Para cargas normales, el servidor crea un nuevo ID de archivo adjunto y escribe un nuevo archivo.

Para los flujos de guardado/actualización de diagramas, sin embargo, el cliente reutiliza intencionalmente un attachmentId existente para que el mismo archivo de diagrama pueda actualizarse en el mismo lugar en lugar de generar un nuevo registro de archivo adjunto cada vez.

Ese comportamiento es legítimo por sí solo.

El problema es que crea una ruta de alto riesgo:

  • una entrada identifica la página que se está autorizando
  • otra entrada identifica el archivo adjunto que se está sobrescribiendo

Siempre que un endpoint combina esas dos responsabilidades, la implementación debe vincularlas exactamente.

Docmost no lo hizo.


Por Qué Vale la Pena Examinar Esta Superficie

Los endpoints mixtos de creación/actualización son lugares comunes para errores de autorización.

La razón es simple:

  • los flujos de creación generalmente se autorizan contra el objeto contenedor
  • los flujos de actualización generalmente se autorizan contra el registro existente
  • si un endpoint intenta hacer ambas cosas, es fácil validar lo incorrecto primero y tratar el segundo identificador como "solo metadatos"

Ese es exactamente el patrón aquí.

POST /api/files/upload validaba que el llamador pudiera editar la página nombrada por pageId.

Pero si también se proporcionaba attachmentId, el servidor cambiaba a una ruta de sobrescritura y seleccionaba un registro de archivo adjunto existente por separado.

Eso generó la pregunta crítica de seguridad:

¿la ruta de sobrescritura prueba que el archivo adjunto seleccionado realmente pertenece a la página autorizada?

La respuesta en las versiones vulnerables fue no.


Causa Raíz

La causa raíz fue una omisión de autorización a través de una clave controlada por el usuario, combinada con un error de lógica booleana en la guardia de sobrescritura.

El flujo vulnerable se veía así:

  1. AttachmentController.uploadFile() leía pageId de los datos del formulario multipart.
  2. Cargaba esa página y llamaba a validateCanEdit(page, user).
  3. Por separado, aceptaba un attachmentId opcional de la misma solicitud.
  4. AttachmentService.uploadFile() cargaba el archivo adjunto existente por ese ID proporcionado por el atacante.
  5. La guardia de sobrescritura intentaba verificar que el archivo adjunto existente coincidiera con la página autorizada.
  6. La guardia usaba && en lugar de rechazar ante cualquier discrepancia.

La guardia vulnerable era:

if (
  existingAttachment.pageId !== pageId &&
  existingAttachment.fileExt !== preparedFile.fileExtension &&
  existingAttachment.workspaceId !== workspaceId
) {
  throw new BadRequestException("File attachment does not match");
}

Esa condición solo rechazaba la solicitud si:

  • el ID de la página no coincidía, y
  • la extensión del archivo no coincidía, y
  • el ID del espacio de trabajo no coincidía

todo al mismo tiempo.

Eso es lo opuesto a lo que debería hacer una guardia de sobrescritura.

Para el caso de ataque real, el atacante permanecía intencionalmente dentro del mismo espacio de trabajo.

Entonces:

  • existingAttachment.workspaceId !== workspaceId era false

Una vez que ese operando se volvía falso, toda la condición && se evaluaba como falsa, incluso si el archivo adjunto pertenecía a una página diferente.

Por lo tanto, el servidor trataba una sobrescritura entre páginas como válida.

Esa fue la primera mitad del error.

La segunda mitad es lo que hizo real el impacto.

Después de la comprobación, el servicio reconstruía la ruta de almacenamiento de destino usando el attachmentId y el nombre de archivo proporcionados por el atacante:

const filePath =
  `${getAttachmentFolderPath(AttachmentType.File, workspaceId)}/` +
  `${attachmentId}/${preparedFile.fileName}`;

Luego, en la ruta de actualización, Docmost solo actualizaba metadatos mutables como:

  • fileSize
  • updatedAt

No volvía a vincular la propiedad a la página del atacante.

Así que la página de la víctima seguía apuntando al mismo registro de archivo adjunto y al mismo ID de archivo adjunto. Solo cambiaban los bytes del archivo subyacente.

Por eso esto no era una discrepancia inofensiva.

Era una primitiva de sobrescritura no autorizada persistente.


Por Qué Esto Es un Problema de Seguridad, No Solo un Error Lógico

Esto no era un error cosmético ni un problema de colisión de nombres de archivo.

El atacante no necesitaba una condición de carrera. El atacante no necesitaba adivinar una ruta aleatoria. El atacante no necesitaba acceso de escritura a la página de la víctima.

Solo necesitaba:

  • acceso de lectura para conocer una referencia de archivo adjunto de la víctima, y
  • acceso de escritura a cualquier otra página en el mismo espacio de trabajo

A partir de ahí, podía reemplazar los bytes del archivo almacenado para el archivo adjunto de otra página mientras la página de la víctima continuaba referenciando y sirviendo ese archivo adjunto como si nada hubiera cambiado.

Eso es una falla directa de integridad.

En términos prácticos, el atacante podía:

Descargar herramienta