Examples

The following examples are based on common use-cases.

Generate

Generation happens fully offline and can run against an arbitrary root directory.

Local System

Generate a CycloneDX SBOM of the current system.

debsbom --progress generate -t cdx -o sbom
# output in sbom.cdx.json

Container Rootfs using Podman

Create the SBOM of a rootless example container. The debsbom tool hereby is used from the host (e.g. from a Python venv).

CRT=$(podman create debian:bookworm)
CHROOT=$(podman unshare podman mount $CRT)
podman unshare debsbom generate -t spdx --root $CHROOT

From Package List

Create the SBOM from a package list. The so provided packages will still be enriched with any available data from the apt cache.

echo "htop 3.4.1-5 amd64" | debsbom generate --from-pkglist
# or in isar manifest format
echo "json-c|0.16-2|libjson-c5:amd64|0.16-2" | debsbom generate --from-pkglist
# or with PURLs
echo "pkg:deb/debian/htop@3.4.1-5?arch=amd64" | debsbom generate --from-pkglist

It further is possible to inject a dpkg status file via stdin (e.g. if you only have that file). The data is then also resolved from the apt-cache (if available), but this usually only makes sense if you don’t have a chroot and want to create the sbom just from the data in the file.

cat path/to/dpkg/status | debsbom generate --from-pkglist

Download

Lookup all packages on the snapshot.debian.org mirror and download all binary and source artifacts referenced in an SBOM:

debsbom --progress \
    download --outdir downloads --sources --binaries sbom.cdx.json
find downloads -mindepth 1 -maxdepth 1
# downloads/.cache   <- debsbom metadata to map packages to artifacts
# downloads/sources  <- files related to source packages (e.g. .dsc, .orig.tar)
# downloads/binaries <- .deb files

It is also possible to download multiple packages by name, version and architecture:

cat <<EOF | debsbom download --binaries --sources
cpp 4:12.2.0-3 amd64
guestfs-tools 1.52.3-1 source
EOF

Alternatively, the download can be executed from the container image:

echo "guestfs-tools 1.52.3-1 source" | \
docker run -v$(pwd)/downloads:/mnt/downloads -i ghcr.io/siemens/debsbom:latest \
    debsbom download --outdir /mnt/downloads --sources

Merge Source Packages

Debian source packages consist of a .dsc file along with one or more related artifacts. The source-merge command takes care of merging all referenced artifacts of a debian source package into a single archive. All referenced files have to be downloaded upfront, by using the download command.

Note

Internally, the dpkg-source command from the dpkg-dev package is used to perform the merge.

The following example merges all debian source packages referenced in the sbom.cdx.json, applies the debian patches and compresses the new artifacts with ZStandard.

debsbom --progress \
    source-merge \
        --compress zstd \
        --apply-patches \
        sbom.cdx.json

Repack Artifacts

The repack command is similar to the source-merge command but performs additional steps to re-layout the downloaded artifacts and recreate the SBOM. The following example generates a standard-bom source distribution archive.

debsbom --progress repack \
    --dldir downloads \
    --outdir source-archive \
    --compress zstd \
    --apply-patches \
    --validate \
    sbom.spdx.json sbom.packed.spdx.json

It further is possible to only repack (and update in the SBOM) a subset of packages. For that, provide both an SBOM, as well as a set of “to-be-processed” packages via stdin.

echo "bash 5.2.37-2 source" | debsbom -v repack sbom-in.json sbom-out.json

Compare SBOMs

The SBOMs produced by debsbom can be further processed with existing tools – for example, the CycloneDX CLI. Comparing two SBOMs directly is outside the scope of debsbom, but you can determine which components have changed by using a short snippet such as the one shown below.

Locate Changes

cyclonedx-cli diff --component-versions --output-format json \
    sbom.old.cdx.json sbom.cdx.json | \
jq -r '.componentVersions[] | select(.added!=[] or .removed!=[]) | {"added": .added[0].purl, "removed": .removed[0].purl}'
# {"added", "purl-a-1.1", "removed": "purl-a-1.0"}
# {...}

A similar output can be generated by just using jq and diff:

diff --color \
    <(jq -r --sort-keys '.components[].purl' sbom.old.cdx.json) \
    <(jq -r --sort-keys '.components[].purl' sbom.cdx.json)

Identify new Components

Consider you only want to know the changed and added components, e.g. for license clearing.

PURLS=$( \
    diff -U0 \
        <(jq -r --sort-keys '.components[].purl' sbom.old.cdx.json) \
        <(jq -r --sort-keys '.components[].purl' sbom.cdx.json) \
        | grep ^+pkg | sed 's/^+//' \
)

The PURLs can be used as input to debsbom to download / merge components:

echo "$PURLS" | debsbom download --sources --binaries

Once downloaded, it is possible to merge the source packages:

echo "$PURLS" | debsbom source-merge --apply-patches

And the same list of packages can be repacked:

echo "$PURLS" | debsbom repack \
    --apply-patches
    sbom.cdx.json \
    sbom.cdx.repacked.json

Export as Graph

The export command allows to convert the SBOM into various graph representations. These can be used as input to graph visualization and analysis tooling (like Gephi).

Note

We recommend to use the SPDX format as input, as this describes inter package relations more precisely.

Convert the SPDX SBOM to GraphML:

debsbom export sbom.spdx.json sbom-graph.graphml