> Documentation version: 3. [HTML page](software-bill-of-materials.html)

<a id="publish-and-consume-software-bills-of-materials"></a>

# Publish and consume software bills of materials

An SBOM describes the components and relationships in a specific release.
Generate it from resolved inputs and final deliverables, then distribute it
with those files. Include shipped first-party, open-source, vendored and
proprietary components. A lockfile or checksum list alone does not describe
release composition.

<a id="risk-component-evidence"></a>

## Risks and controls for component evidence

An inventory can omit components or describe another binary while passing
schema validation. Bind claims to exact subjects and preserve uncertainty.
Review resolved inputs and composition metadata, validate subject hashes and
graph references, and test queries for known transitive and build-only
components. Supplier imports must match the locked artifact and reviewed
document digest. These checks detect inconsistent records; they do not prove
that discovery is complete, a supplier authored the document, or a vulnerability
match is exploitable.

<a id="share-generation-validation-and-publication-responsibilities"></a>

## Share generation, validation and publication responsibilities

The read-only build task owns generation and checking. Blueprint supplies
resolved identities and its SBOM tool; the repository supplies deliverables and
reviewed metadata for licenses, native libraries, vendored code and composition.
A tool selected in an environment is not necessarily contained in its output.

Inspect the resolved specification and lock without provisioning inputs, then
bind the inventory to final artifact bytes after the build. Missing information
is a declared gap. Do not fetch, rebuild or scan unrelated store trees merely
to make an inventory appear complete.

The publisher receives inert files and rechecks their transfer bindings. It
never evaluates candidate Blueprint configuration or regenerates an SBOM.
Provenance admission and vulnerability analysis have separate purposes; see
[artifact admission](artifact-verification.md#separate-admission-from-routine-use).

<a id="declare-what-the-inventory-covers"></a>

## Declare what the inventory covers

Give each deliverable a subject with its release URL, filename, version, target
and final SHA-256. Each subject needs its own component graph, whether documents
are separate or combined.

| Deliverable | Scope |
| --- | --- |
| Roc source bundle | Shipped source, vendored code and transitive package/platform dependencies. Distinguish contained code from dependencies fetched later. |
| Native executable or linker-input archive | Included libraries, static inputs and generated or embedded code. Record externally provided runtime dependencies separately. |
| Examples or documentation archive | Distributed code, scripts, fonts and third-party material, with example dependencies distinguished from sibling binaries. |
| Build and test inputs | Compiler and tooling identities with build/test relationships. Using a tool does not establish that it ships in the output. |

Record generation context, inspected inputs, exclusions and gaps in the
machine-processable document. Include transitive components or immutable,
hash-bound supplier documents. Unknown information needs a reason and contact;
an empty inventory must not stand for failed discovery. A source inventory alone
does not establish the composition of an optimized executable.

<a id="choose-an-interoperable-format"></a>

## Choose an interoperable format

Use the SPDX or CycloneDX formats supported by the reviewed producer and
consumers. The shared sidecar action produces SPDX JSON-LD and CycloneDX JSON,
with optional SPDX 2.3 output from the same inventory. Give each document a
unique identity, revision, creation time, author and generator identity,
separately from its subject’s software version.

Component records need a producer, canonical name, exact version or revision,
stable identifier, immutable source/download identity, available artifact hash,
license information and explicit relationships. Preserve upstream identities
and local patch revisions; do not invent ecosystem identifiers to obtain a
vulnerability match. Distinguish containment, runtime dependencies and build/test
use. Record incomplete coverage explicitly.

The
[SPDX package specification](https://spdx.github.io/spdx-spec/v2.3.1/package-information/)
and [CycloneDX dependency graph](https://cyclonedx.org/use-cases/software-dependencies/)
describe the corresponding records and relationships.

<a id="generate-and-validate-during-the-release-build"></a>

## Generate and validate during the release build

Use the same generation task and validation policy for a pull-request dry run
and the release:

1. Build and test the deliverables, then calculate their final hashes.


2. Generate sidecars for those exact files from resolved inputs and reviewed
   supplementary metadata. Keep sidecars outside the hashed subject archive.

3. Check the declared schema and semantics: subjects, targets, hashes, unique
   identifiers, graph references and coverage against known resolved inputs.

4. Query a known transitive component and distinguish a build-only tool from
   shipped code. A syntactically valid document is insufficient evidence.

5. Transfer the tested files and checked sidecars from the same run. Recheck
   downloaded bindings before attestation and uploaded bytes before publication.

Pin and cache generators like other tools. Routine checks use local schemas and
metadata; advisory queries belong in separate scheduled or manual analysis.
Review supplementary metadata with the build recipe instead of editing generated
SBOMs by hand.

<a id="generate-sidecars-with-the-shared-actions"></a>

### Generate sidecars and chain suppliers' SBOMs with the shared actions

Keep ` sbom/composition.json ` under review, with a composition per target when
needed. The complete ` examples/sbom-chain/ ` release demonstrates source bundles,
native executables and supplier imports.

- [` actions/fetch-dependency-sboms `](actions.md#fetch-dependency-sboms)
  reads the lock’s public report, fetches supplier sidecars and records their
  identities and digests in ` sbom/imports.json `.

- [` actions/sbom-sidecars `](actions.md#sbom-sidecars) runs Blueprint’s
  admitted ` inspect `, ` bind ` and ` check ` tool after final files exist. It combines
  the specification, lock, composition and imports, then returns the subject,
  sidecar and manifest paths for testing, attestation and publication.

The action revision fixes reviewed tool records in
` actions/setup-blueprint/sbom-tools.json `. ` Blueprint.roc ` selects a recorded
release. Native tools are admitted by SHA-256; app bundles use a verified content
hash and the recorded compiler. Output manifests must match that tool’s recorded
profile. Run these repository-evaluating actions only in read-only jobs.

Only source ` .tar.zst ` bundles enter archive member enumeration. Each member must
be accounted for by the reviewed composition or generated member records.
Other subjects, including ZIP and PDF files, require a reviewed composition and
receive their own final-byte hashes and sidecars.

Commit the imports record so changed supplier documents require review and the
release build can reuse known bytes. A scheduled fetch can propose updates.
Fetching during a release is supported but adds a network dependency; changed
or missing recorded bytes fail rather than being adopted silently.

A locked dependency requires a bound supplier document or a reviewed
` unavailable_sboms ` reason and contact. The fetch action emits incomplete stubs
for maintainers to resolve, reports opt-outs whose suppliers provide sidecars,
and rejects document identities that do not match the locked file. Tree/NAR
digests do not substitute for a file SHA-256. Gaps remain visible in document
coverage and the job summary.

<a id="validate-a-declared-release-inventory"></a>

### Validate a declared release inventory

The sidecar action returns a ` roc-automation-sbom-evidence-v1 ` envelope with
subject and sidecar names, sizes, hashes, formats and targets, bound to the source
commit, producing run/attempt and per-subject inventory digest. Component graphs
stay in the standard SBOM documents; the envelope is a transfer record.

The shared package workflow transfers this record as ` dist/sbom-evidence.json `
and excludes it from published assets. Before attestation, its reviewed controller
checks the build job’s expected subject/format set, source and producer identity,
and exact downloaded bytes against the envelope and Blueprint manifests. It also
checks optional SPDX 2.3 sidecars. Publication retries use the attempt that
produced the candidate, not the retrying job’s attempt.

The controller reads bounded regular files and rejects duplicate JSON,
noncanonical paths, symlinks, hard-link aliases and inconsistent bindings.
Transfer/tampering tests exercise generated records and retries without a
Blueprint tool or compiler on ` PATH `. This establishes final-byte consistency,
not composition completeness or provenance of producer declarations.

<a id="reuse-the-existing-publication-paths"></a>

### Reuse the existing publication paths

Pass an explicit asset list to ` actions/publish-release `, including required
sidecars and manifests. Its draft recovery and download/hash checks preserve
the tested bytes. For linker-input releases, follow the versioned
[publisher contract](linker-input-releases.md#trusted-publisher-contract).

Keep signing authority separate from generation. An attestation job runs pinned
reviewed code on inert files from the selected build run, bound to that run’s
source and subjects. It never executes candidate sources. Provenance about an
SBOM file and an SBOM statement about software have different subjects; neither
establishes the accuracy of the composition claims.

<a id="distribute-and-retain-the-evidence"></a>

## Distribute and retain the evidence

Publish ` <asset-name>.spdx.json ` or ` <asset-name>.cdx.json ` alongside immutable
release assets. Release notes link the subject mapping, formats, scope, gaps
and signature/attestation evidence. Short-lived workflow artifacts are not the
downstream distribution channel.

Retain documents and referenced supplier SBOMs for supported releases. Give
authorized recipients sufficient identity and relationship data for restricted
components. Public records must exclude credentials and developer paths.

Correct an SBOM at a new immutable document revision bound to the unchanged
subject digest. Retain the original and link the correction; do not replace a
published asset. Changed software bytes require a new software release.

<a id="consume-and-act-on-the-inventory"></a>

## Consume and act on the inventory

At adoption, validate the selected artifact’s SBOM format and subject hash,
verify expected provenance, and retain the admitted records with that artifact’s
identity. Preserve supplier identities and relationships when incorporating
components into your own SBOM.

Query component identifiers, revisions and hashes for supported release targets
when investigating an advisory. Maintainers assess matches, patches and actual
usage. An absent query result in an incomplete inventory establishes neither
component absence nor freedom from vulnerabilities. Product-specific response
decisions remain with maintainers.

