SBOM
SBOM de Docker: cómo generar una y qué se le escapa
Puede obtener una SBOM de una imagen Docker con un solo comando, durante el build con BuildKit o después con Docker Scout o Syft. Cada uno lee los metadatos de paquetes que encuentra en la imagen. Ese es el registro correcto de lo que contiene la imagen, hasta donde llegan los metadatos. No es un registro de cómo se compiló la imagen.
Actualizado el
Cómo generar una SBOM para una imagen Docker
Hay tres formas habituales. BuildKit puede escribir la SBOM mientras compila la imagen y adjuntarla a ella como atestación. Docker Scout y Syft generan una a partir de una imagen que ya existe, en local o en un registro.
Durante el build, con BuildKit
Añada --sbom=true, o su forma larga --attest type=sbom, a docker buildx build. BuildKit ejecuta su plugin de escáner Syft sobre el resultado y adjunta la SBOM a la imagen como documento SPDX JSON. Compile con el exportador local para ver la SBOM antes de publicar nada:
# Build the image, attach an SBOM attestation and push it
docker buildx build --sbom=true -t registry.example.com/app:1.0 --push .
# The long form of the same option
docker buildx build --attest type=sbom -t registry.example.com/app:1.0 --push .
# Check the SBOM before pushing: write the build result to ./out
docker buildx build --sbom=true --output type=local,dest=out .
# out/sbom.spdx.json is the SBOM Leer la SBOM adjunta a una imagen
docker buildx imagetools inspect recupera la atestación del registro. Todo lo relacionado con la SBOM está bajo .SBOM en su plantilla de Go:
# Print the SPDX document attached to the image
docker buildx imagetools inspect registry.example.com/app:1.0 \
--format "{{ json .SBOM.SPDX }}"
# List each package and its version
docker buildx imagetools inspect registry.example.com/app:1.0 \
--format "{{ range .SBOM.SPDX.packages }}{{ .name }}@{{ .versionInfo }}{{ println }}{{ end }}" A partir de una imagen existente, con Docker Scout
docker scout sbom utiliza la atestación de SBOM de la imagen cuando existe. Si no existe, indexa por sí mismo el contenido de la imagen. Imprime JSON por defecto y escribe en un archivo con --output:
# List the packages in an image
docker scout sbom --format list registry.example.com/app:1.0
# Write an SPDX or CycloneDX SBOM to a file
docker scout sbom --format spdx --output app.spdx.json registry.example.com/app:1.0
docker scout sbom --format cyclonedx --output app.cdx.json registry.example.com/app:1.0 A partir de una imagen existente, con Syft
Syft es el escáner de código abierto en el que se basa el plugin de BuildKit. Apúntelo a una imagen y elija el formato con -o. Añada =file para escribir cada formato en su propio archivo:
# CycloneDX JSON to the terminal
syft registry.example.com/app:1.0 -o cyclonedx-json
# Both formats, each to its own file
syft registry.example.com/app:1.0 -o spdx-json=app.spdx.json -o cyclonedx-json=app.cdx.json ¿SPDX o CycloneDX?
Las atestaciones de BuildKit siempre son SPDX. Docker Scout escribe SPDX o CycloneDX, y Syft escribe ambos, entre otros formatos. Los dos estándares enumeran paquetes, versiones, licencias y package URL, de modo que la elección suele depender de la herramienta que lea después la SBOM. Consulte CycloneDX vs SPDX para ver las diferencias.
Cómo construye una SBOM un escáner de imágenes
Todas estas herramientas funcionan igual. Desempaquetan las capas de la imagen y leen los metadatos de paquetes que encuentran: la base de datos de paquetes del sistema operativo y los metadatos que dejan los gestores de paquetes de cada lenguaje. Cada paquete que pueden identificar se convierte en una entrada de la SBOM, incluidos los paquetes procedentes de la imagen base.
Incluir las etapas de build y el contexto de build
Por defecto, BuildKit solo escanea la etapa final. En un build de varias etapas, los compiladores, las herramientas de build y los paquetes utilizados en etapas anteriores no están en la imagen final, de modo que tampoco están en su SBOM. La documentación de atestaciones de SBOM de Docker describe dos argumentos de build que amplían el escaneo. BUILDKIT_SBOM_SCAN_STAGE añade una etapa y BUILDKIT_SBOM_SCAN_CONTEXT añade el contexto de build:
# syntax=docker/dockerfile:1
# Scan the build context as well as the image
ARG BUILDKIT_SBOM_SCAN_CONTEXT=true
FROM golang:1.25 AS build
# Include this build stage in the SBOM
ARG BUILDKIT_SBOM_SCAN_STAGE=true
WORKDIR /src
COPY . .
RUN go build -o /out/app .
FROM scratch
COPY --from=build /out/app /app
ENTRYPOINT ["/app"] Ambos deben declararse con ARG en el Dockerfile. Definirlos solo con --build-arg no tiene ningún efecto, aunque --build-arg puede anular un valor que declare el Dockerfile. Con el exportador local, cada etapa escaneada obtiene su propio archivo, como sbom-build.spdx.json junto a sbom.spdx.json.
Lo que sigue escapándose a un escaneo
El escaneo de etapas cierra una laguna. Sin embargo, el escáner sigue leyendo archivos, y parte de lo que utiliza un build no deja ningún archivo, o ninguno que pueda identificar:
- Archivos sin metadatos de paquetes. Un binario descargado con
curl, un tarball desempaquetado en un pasoRUNo código de terceros copiado en la imagen. Algunos binarios llevan información de build que un escáner puede leer, como los binarios de Go; muchos no. - Lo que el build descargó y eliminó. Un paquete o instalador que un paso
RUNdescarga, utiliza y elimina en la misma capa no deja nada en el sistema de archivos que un escáner pueda leer, sea o no la etapa final. - Cómo entraron las cosas. Una SBOM procedente de un escaneo enumera lo que hay. No dice de qué registro o host procede un paquete ni qué paso lo descargó.
- Las etapas que no marcó. El escaneo de etapas es opcional, por etapa o global. Una etapa sin el argumento sigue quedando fuera.
- Configuración del escaneo. Lo que aparece depende de cómo se ejecute el escáner. En un proyecto, un solo flag de Syft decide si los paquetes npm aparecen o no en el resultado.
Por qué importa
Una herramienta de build o una imagen base comprometida afecta a lo que usted distribuye aunque nunca aparezca en la imagen final. Y un binario sin metadatos puede contener una vulnerabilidad a la que no apunta ninguna entrada de la SBOM. Cuando llega un aviso, necesita saber qué entró en el build de la imagen además de qué hay en ella.
Registre también el build
La SBOM de la imagen responde a qué hay dentro de la imagen. Un registro del build responde a qué incorporó el build: las imágenes base que descargó y los paquetes que descargó cada paso, incluidas las dependencias ocultas que ningún lockfile enumera. CRACI lo registra mientras se ejecuta su job de GitHub Actions, mediante un proxy que entiende de paquetes en el runner, y la API devuelve SBOM, trazas de red y procedencia del job. Utilice la SBOM de la imagen para lo que distribuye y el registro del build para saber cómo se hizo.
Consulte la comparativa de herramientas de SBOM, SBOM durante el build y cómo generar una SBOM en GitHub Actions.
SBOM de Docker: preguntas frecuentes
¿Cómo genero una SBOM para una imagen Docker?
Hay tres formas habituales. Añada --sbom=true a docker buildx build y BuildKit adjuntará a la imagen una SBOM SPDX. Ejecute docker scout sbom sobre una imagen existente. O ejecute Syft, por ejemplo syft IMAGE -o cyclonedx-json. Las tres leen los paquetes que encuentran en la imagen.
¿Qué es un escáner de SBOM?
Una herramienta que lee archivos, como un directorio de código fuente, un lockfile o una imagen de contenedor, y escribe una SBOM de los paquetes que puede identificar. Syft, Trivy, Docker Scout y el plugin Syft de BuildKit son escáneres de SBOM. Describen los archivos que tienen delante, no el build que los produjo.
¿Qué formato de SBOM produce Docker?
Las atestaciones de BuildKit son documentos SPDX JSON adjuntos a la imagen. Docker Scout puede imprimir una lista de paquetes o escribir SPDX o CycloneDX. Syft escribe ambos, y más. Elija el formato que espere la herramienta que consume la SBOM.
¿Cómo construye un escáner una SBOM a partir de una imagen Docker?
Desempaqueta las capas de la imagen y lee los metadatos de paquetes que encuentra: la base de datos de paquetes del sistema operativo y los archivos de paquetes de cada lenguaje, como los metadatos de paquetes npm o Python instalados. Cada paquete que puede identificar se convierte en una entrada de la SBOM.
¿Por qué podría faltar un componente en la SBOM de una imagen?
Porque solo puede enumerar lo que puede identificar en los archivos que lee. Un binario descargado con curl no lleva metadatos de paquetes, un paquete que un paso del build descargó y eliminó no deja nada que leer, y las etapas de build anteriores quedan fuera salvo que active el escaneo de etapas.
¿Sigue siendo útil la SBOM de una imagen?
Sí. Es el registro correcto de lo que hay dentro de la imagen que distribuye, incluidos los paquetes de la imagen base. Simplemente no describe cómo se compiló la imagen, así que combínela con un registro del build cuando eso importe.
Vea lo que incorporó el build de su imagen
Ejecute un build de imagen en CRACI y compare su registro de imágenes base y paquetes descargados con la SBOM de imagen de su escáner.
Reservar una demo