From f40a23791cc27596d733d5ea05d425200128904b Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 10 Mar 2022 12:29:26 -0500 Subject: [PATCH 01/12] Proposes a mechanism for platforms, when running builds, to provide an sbom for the run image Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 86 +++++++++++++++++++++++++++++++++++++ 1 file changed, 86 insertions(+) create mode 100644 text/0000-run-image-sbom.md diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md new file mode 100644 index 000000000..13873655b --- /dev/null +++ b/text/0000-run-image-sbom.md @@ -0,0 +1,86 @@ +# Meta +[meta]: #meta +- Name: Run Image SBOM +- Start Date: 2022-03-09 +- Author(s): natalieparellano +- Status: Draft +- RFC Pull Request: (leave blank) +- CNB Pull Request: (leave blank) +- CNB Issue: (leave blank) +- Supersedes: https://github.com/buildpacks/rfcs/pull/186 + +# Summary +[summary]: #summary + +This RFC proposes a mechanism for platforms, when running builds, to provide an sbom for the run image that will be included in the final app image. + +# Definitions +[definitions]: #definitions + +- Run Image: A container image that serves as a base image for application images in the buildpack toolchain. +- SBOM (Software Bill Of Materials) / BOM: A list of components in a piece of software. Software vendors often create products by assembling open source and commercial software components. The SBOM describes the components in a product. In case of buildpacks the SBOM describes the contents of the various layers, buildpacks, base images and the output app container. +- Attestation: authenticated metadata about one or more software artifacts, as per the SLSA Attestation Model (see [here](https://github.com/in-toto/attestation) and [here](https://github.com/sigstore/cosign#in-toto-attestations)). +- Cosign sbom attachment: an sbom object represented as an OCI Image Manifest V1 (see [here](https://github.com/sigstore/cosign/blob/main/specs/SBOM_SPEC.md)). + +# Motivation +[motivation]: #motivation + +This RFC serves as an addendum to [#RFC 95: Structured SBOMs](https://github.com/buildpacks/rfcs/blob/main/text/0095-sbom.md), which introduced a structured way for buildpacks to provide an sbom for dependencies installed at build time. For a full depiction of dependencies within a container image, container scanning tools would _also_ need an sbom for OS packages that were installed on the run image when it was created. + +# What it is +[what-it-is]: #what-it-is + +- Define the target persona: platform operator, platform implementor, end user. +- If applicable, provide sample error messages, deprecation warnings, or migration guidance. + - The lifecycle could warn if a usable run image sbom is not provided. + +Example invocation: `/cnb/lifecycle/exporter -run-image my-run-image -run-image-sbom my-run-image-sbom.json my-app-image` + +# How it Works +[how-it-works]: #how-it-works + +Following the invocation above, the exported app image would contain: +* `my-run-image-sbom.json` somewhere in `/layers/sbom`; suggestions: + * `/layers/sbom/launch/run-image/sbom.` (this would make `run-image` a reserved buildpack id) + * `/layers/sbom/run-image/sbom.` + * ? + +The accepted media types would be: +* `application/vnd.cyclonedx+json` with ext `cdx.json` +* `application/spdx+json` with ext `spdx.json` +* `application/vnd.syft+json` with ext `syft.json` +* others? + +# Drawbacks +[drawbacks]: #drawbacks + +Why should we *not* do this? Leaving the location of the run image sbom unspec'd could make it harder for logic-less platforms like Tekton to use the creator. However, a CNB-provided "prepare" operation ([currently under discussion](https://github.com/buildpacks/rfcs/pull/202)) could make this easier. For example, a preparer could look for a run image sbom in a file, attestation, attachment, or layer (picking the first one it finds) and provide the data as a file to the creator. The Tekton task that uses the creator currently already has a ["prepare" step](https://github.com/tektoncd/catalog/blob/4bf8b57aa105f0c7ce05fc122a11b1b0d5822fcd/task/buildpacks/0.3/buildpacks.yaml#L70-L121) which could be modified to invoke a preparer binary. + +# Alternatives +[alternatives]: #alternatives + +- What other designs have been considered? [Adding the sbom as a layer](https://github.com/buildpacks/rfcs/pull/186) to the run image and adding its diffID as a label. Some [concerns](https://github.com/buildpacks/rfcs/pull/186#issuecomment-1043348097) with this proposal included: + * Special tooling is required to create the run image (because we don't know the diffID ahead of time) + * The run image may [fall out of date](https://github.com/buildpacks/rfcs/pull/186#discussion_r773246636) in a way that is not obvious + * We don't want to "pick a winner" just yet for the mechanism for attaching sboms to the run image +- Why is this proposal the best? This frees platforms to choose their own method of attaching sboms to the run image, while providing a standardized way to consume a complete sbom for the app image. +- What is the impact of not doing this? Each platform will have to come up with its own way of attaching run image sboms to the app image. + +# Prior Art +[prior-art]: #prior-art + +- [#RFC 95: Structured SBOMs](https://github.com/buildpacks/rfcs/blob/main/text/0095-sbom.md) + +# Unresolved Questions +[unresolved-questions]: #unresolved-questions + +- What should be the path of the run image sbom within the image? +- Should the run image sbom be part of the layer containing the buildpack-provided launch sboms? This layer is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. Is there a better layer / label? +- What should be all the accepted media types / extensions? + +- What related issues do you consider out of scope for this RFC that could be addressed in the future independently of the solution that comes out of this RFC? + - The existence or behavior of a preparer binary that knows how to download run image sboms. + +# Spec. Changes (OPTIONAL) +[spec-changes]: #spec-changes +Does this RFC entail any proposed changes to the core specifications or extensions? New field on the exporter. Potentially a new label. From ab9c769aed4fa363ff8dc03366bd885f86794e88 Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 10 Mar 2022 14:57:51 -0500 Subject: [PATCH 02/12] Apply suggestions from code review Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index 13873655b..92f62cf10 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -75,7 +75,7 @@ Why should we *not* do this? Leaving the location of the run image sbom unspec'd [unresolved-questions]: #unresolved-questions - What should be the path of the run image sbom within the image? -- Should the run image sbom be part of the layer containing the buildpack-provided launch sboms? This layer is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. Is there a better layer / label? +- How should the layer containing the run image sbom be designated? This layer containing the buildpack-provided sbom is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. - What should be all the accepted media types / extensions? - What related issues do you consider out of scope for this RFC that could be addressed in the future independently of the solution that comes out of this RFC? @@ -83,4 +83,4 @@ Why should we *not* do this? Leaving the location of the run image sbom unspec'd # Spec. Changes (OPTIONAL) [spec-changes]: #spec-changes -Does this RFC entail any proposed changes to the core specifications or extensions? New field on the exporter. Potentially a new label. +Does this RFC entail any proposed changes to the core specifications or extensions? New fields on the exporter and rebaser. A new label on the app image to designate the layer containing the run image sbom. From 167686d525be5785ff49a0cabd4be77e50c3bb4b Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Tue, 15 Mar 2022 14:42:46 -0400 Subject: [PATCH 03/12] Update text/0000-run-image-sbom.md Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index 92f62cf10..c6a1d231c 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -75,7 +75,7 @@ Why should we *not* do this? Leaving the location of the run image sbom unspec'd [unresolved-questions]: #unresolved-questions - What should be the path of the run image sbom within the image? -- How should the layer containing the run image sbom be designated? This layer containing the buildpack-provided sbom is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. +- How should the layer containing the run image sbom be designated? This layer containing the buildpack-provided sbom is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. #186 proposed `io.buildpacks.base.sbom` for the layer containing the run image sbom, and `io.buildpacks.app.sbom` for the layer containing the buildpack-provided sbom (in addition to `io.buildpacks.lifecycle.metadata`). - What should be all the accepted media types / extensions? - What related issues do you consider out of scope for this RFC that could be addressed in the future independently of the solution that comes out of this RFC? From 5f07fa736b42a4e81acddf0c8949ca5431d8bcce Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 24 Mar 2022 15:01:31 -0400 Subject: [PATCH 04/12] Apply suggestions from code review Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index c6a1d231c..513f9a923 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -30,11 +30,16 @@ This RFC serves as an addendum to [#RFC 95: Structured SBOMs](https://github.com # What it is [what-it-is]: #what-it-is +```suggestion +# What it is + +This RFC proposes a mechanism for platforms to supply the SBOM for a run image at build time, leaving the method of storing and associating the SBOM to the run image unspec'd. The lifecycle would ingest the provided SBOM and place it in a spec'd location in the final app image. A label would be used to designate the layer containing the SBOM for the run image. + - Define the target persona: platform operator, platform implementor, end user. - If applicable, provide sample error messages, deprecation warnings, or migration guidance. - The lifecycle could warn if a usable run image sbom is not provided. -Example invocation: `/cnb/lifecycle/exporter -run-image my-run-image -run-image-sbom my-run-image-sbom.json my-app-image` +Example invocation: `/cnb/lifecycle/exporter -run-image my-run-image -run-image-sbom my-app-image` # How it Works [how-it-works]: #how-it-works @@ -54,7 +59,8 @@ The accepted media types would be: # Drawbacks [drawbacks]: #drawbacks -Why should we *not* do this? Leaving the location of the run image sbom unspec'd could make it harder for logic-less platforms like Tekton to use the creator. However, a CNB-provided "prepare" operation ([currently under discussion](https://github.com/buildpacks/rfcs/pull/202)) could make this easier. For example, a preparer could look for a run image sbom in a file, attestation, attachment, or layer (picking the first one it finds) and provide the data as a file to the creator. The Tekton task that uses the creator currently already has a ["prepare" step](https://github.com/tektoncd/catalog/blob/4bf8b57aa105f0c7ce05fc122a11b1b0d5822fcd/task/buildpacks/0.3/buildpacks.yaml#L70-L121) which could be modified to invoke a preparer binary. +Why should we *not* do this? Leaving the location of the run image sbom unspec'd (as opposed to baking it into the run image at a specific location) could make it harder for logic-less platforms like Tekton to use the creator. +* Possible mitigation: a CNB-provided "prepare" operation ([currently under discussion](https://github.com/buildpacks/rfcs/pull/202)) could make this easier. For example, a preparer could look for a run image sbom in a file, attestation, attachment, or layer (picking the first one it finds) and provide the data as a file to the creator. The Tekton task that uses the creator currently already has a ["prepare" step](https://github.com/tektoncd/catalog/blob/4bf8b57aa105f0c7ce05fc122a11b1b0d5822fcd/task/buildpacks/0.3/buildpacks.yaml#L70-L121) which could be modified to invoke a preparer binary. # Alternatives [alternatives]: #alternatives From da893a6e49a6a68a4b62d0d9579a9a8189a70a24 Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 24 Mar 2022 15:05:05 -0400 Subject: [PATCH 05/12] Fix formatting Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 3 --- 1 file changed, 3 deletions(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index 513f9a923..4da600b6a 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -30,9 +30,6 @@ This RFC serves as an addendum to [#RFC 95: Structured SBOMs](https://github.com # What it is [what-it-is]: #what-it-is -```suggestion -# What it is - This RFC proposes a mechanism for platforms to supply the SBOM for a run image at build time, leaving the method of storing and associating the SBOM to the run image unspec'd. The lifecycle would ingest the provided SBOM and place it in a spec'd location in the final app image. A label would be used to designate the layer containing the SBOM for the run image. - Define the target persona: platform operator, platform implementor, end user. From b8f693667a5d429558321cf179c97e19774e735f Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 24 Mar 2022 15:52:34 -0400 Subject: [PATCH 06/12] Further updates following conversation in working group Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 42 +++++++++++++++++++++++++++++++++---- 1 file changed, 38 insertions(+), 4 deletions(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index 4da600b6a..88eca6737 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -36,16 +36,22 @@ This RFC proposes a mechanism for platforms to supply the SBOM for a run image a - If applicable, provide sample error messages, deprecation warnings, or migration guidance. - The lifecycle could warn if a usable run image sbom is not provided. -Example invocation: `/cnb/lifecycle/exporter -run-image my-run-image -run-image-sbom my-app-image` +Example invocation: +* build: `/cnb/lifecycle/exporter -run-image my-run-image -run-image-sbom my-app-image` +* rebase: `/cnb/lifecycle/rebaser -run-image my-new-run-image -run-image-sbom my-app-image` # How it Works [how-it-works]: #how-it-works -Following the invocation above, the exported app image would contain: +## Build + +Following the build invocation above, the exported app image would contain: * `my-run-image-sbom.json` somewhere in `/layers/sbom`; suggestions: + * `/layers/sbom/launch/base/sbom.` (this would make `base` a reserved buildpack id) * `/layers/sbom/launch/run-image/sbom.` (this would make `run-image` a reserved buildpack id) * `/layers/sbom/run-image/sbom.` * ? +* An `io.buildpacks.sbom.base` label containing the diffID of the layer containing the run image sbom The accepted media types would be: * `application/vnd.cyclonedx+json` with ext `cdx.json` @@ -53,11 +59,39 @@ The accepted media types would be: * `application/vnd.syft+json` with ext `syft.json` * others? +## Rebase + +Following the rebase invocation above, the exported app image would contain: +* `my-new-run-image-sbom.json` somewhere in `/layers/sbom` +* The layer containing the old run image sbom would be removed +* The `io.buildpacks.sbom.base` label would be updated to contain the diffID of the layer containing the new run image sbom + +## When a run image has an sbom baked in + +A platform could provide a run image that already has an sbom baked in - i.e., has a layer containing an sbom that is advertised in `io.buildpacks.sbom.base`. In this case, the lifecycle could just do nothing, and the final app image would contain an sbom in the expected location with the expected label. This (as in #186) runs the risk that the sbom baked into the run image has fallen out of date. + +If a platform provided a run image with a baked in sbom and also supplied the `-run-image-sbom` argument, the lifecycle could replace the baked in sbom with the new sbom, much like rebase. + +## With Dockerfiles + +https://github.com/buildpacks/rfcs/pull/173 proposes allowing the run image to be extended or swapped using Dockerfiles. There are a few scenarios that could occur: +* The run image is extended - the lifecycle would need to run a `genpkgs` executable after Dockerfiles have been applied. The result of this invocation would replace the `io.buildpacks.sbom.base` label on the extended run image. In this scenario, the build would proceed according to the process outlined in "When a run image has an sbom baked in". +* The run image is swapped for a new run image that already has a `io.buildpacks.sbom.base` label. In this scenario, the lifecycle would NOT run `genpkgs`, and the build would proceed according to the process outlined in "When a run image has an sbom baked in". +* The run image is swapped for a new run image that does not have a `io.buildpacks.sbom.base` label. In this scenario, there are a couple things that could occur: + * The lifecycle could run `genpkgs` to produce a run image sbom for use during export + * The lifecycle could return the new run image reference to the platform, expecting the platform to locate an sbom + +## With pack + +`pack` could make use of the preparer binary described below to download a run image sbom prior to running the exporter. When Dockerfiles are supported, the preparer invocation would need to happen after the `extender` has run to cover the case where a new run image is selected. + # Drawbacks [drawbacks]: #drawbacks -Why should we *not* do this? Leaving the location of the run image sbom unspec'd (as opposed to baking it into the run image at a specific location) could make it harder for logic-less platforms like Tekton to use the creator. -* Possible mitigation: a CNB-provided "prepare" operation ([currently under discussion](https://github.com/buildpacks/rfcs/pull/202)) could make this easier. For example, a preparer could look for a run image sbom in a file, attestation, attachment, or layer (picking the first one it finds) and provide the data as a file to the creator. The Tekton task that uses the creator currently already has a ["prepare" step](https://github.com/tektoncd/catalog/blob/4bf8b57aa105f0c7ce05fc122a11b1b0d5822fcd/task/buildpacks/0.3/buildpacks.yaml#L70-L121) which could be modified to invoke a preparer binary. +Why should we *not* do this? Leaving the location of the run image sbom unspec'd (as opposed to baking it into the run image at a specific location) could make it harder for logic-less platforms like Tekton to use the creator. + +## preparer binary +* A possible mitigation to the drawback noted above would be a CNB-provided "prepare" operation ([currently under discussion](https://github.com/buildpacks/rfcs/pull/202)) could make this easier. For example, a preparer could look for a run image sbom in a file, attestation, attachment, or layer (picking the first one it finds) and provide the data as a file to the creator. The Tekton task that uses the creator currently already has a ["prepare" step](https://github.com/tektoncd/catalog/blob/4bf8b57aa105f0c7ce05fc122a11b1b0d5822fcd/task/buildpacks/0.3/buildpacks.yaml#L70-L121) which could be modified to invoke a preparer binary. # Alternatives [alternatives]: #alternatives From 6a269990d2cebbf4b7ca892a0b7b72d994e89c9e Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Fri, 25 Mar 2022 09:49:39 -0400 Subject: [PATCH 07/12] Update text/0000-run-image-sbom.md Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index 88eca6737..1f9c209d1 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -91,7 +91,7 @@ https://github.com/buildpacks/rfcs/pull/173 proposes allowing the run image to b Why should we *not* do this? Leaving the location of the run image sbom unspec'd (as opposed to baking it into the run image at a specific location) could make it harder for logic-less platforms like Tekton to use the creator. ## preparer binary -* A possible mitigation to the drawback noted above would be a CNB-provided "prepare" operation ([currently under discussion](https://github.com/buildpacks/rfcs/pull/202)) could make this easier. For example, a preparer could look for a run image sbom in a file, attestation, attachment, or layer (picking the first one it finds) and provide the data as a file to the creator. The Tekton task that uses the creator currently already has a ["prepare" step](https://github.com/tektoncd/catalog/blob/4bf8b57aa105f0c7ce05fc122a11b1b0d5822fcd/task/buildpacks/0.3/buildpacks.yaml#L70-L121) which could be modified to invoke a preparer binary. +* A possible mitigation to the drawback noted above would be a CNB-provided "prepare" operation ([currently under discussion](https://github.com/buildpacks/rfcs/pull/202)). For example, a preparer could look for a run image sbom in a file, attestation, attachment, or layer (picking the first one it finds) and provide the data as a file to the creator. The Tekton task that uses the creator currently already has a ["prepare" step](https://github.com/tektoncd/catalog/blob/4bf8b57aa105f0c7ce05fc122a11b1b0d5822fcd/task/buildpacks/0.3/buildpacks.yaml#L70-L121) which could be modified to invoke a preparer binary. # Alternatives [alternatives]: #alternatives From 1c69616b2ed31c8075a1678423dc23993a46fb03 Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 31 Mar 2022 09:41:26 -0400 Subject: [PATCH 08/12] Be more opinionated about the location of the SBOM within the image Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 45 ++++++++++++++++++++++--------------- 1 file changed, 27 insertions(+), 18 deletions(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index 1f9c209d1..07999bcf2 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -37,8 +37,8 @@ This RFC proposes a mechanism for platforms to supply the SBOM for a run image a - The lifecycle could warn if a usable run image sbom is not provided. Example invocation: -* build: `/cnb/lifecycle/exporter -run-image my-run-image -run-image-sbom my-app-image` -* rebase: `/cnb/lifecycle/rebaser -run-image my-new-run-image -run-image-sbom my-app-image` +* build: `/cnb/lifecycle/exporter -run-image my-run-image -run-image-sbom my-app-image` +* rebase: `/cnb/lifecycle/rebaser -run-image my-new-run-image -run-image-sbom my-app-image` # How it Works [how-it-works]: #how-it-works @@ -46,25 +46,35 @@ Example invocation: ## Build Following the build invocation above, the exported app image would contain: -* `my-run-image-sbom.json` somewhere in `/layers/sbom`; suggestions: - * `/layers/sbom/launch/base/sbom.` (this would make `base` a reserved buildpack id) - * `/layers/sbom/launch/run-image/sbom.` (this would make `run-image` a reserved buildpack id) - * `/layers/sbom/run-image/sbom.` - * ? -* An `io.buildpacks.sbom.base` label containing the diffID of the layer containing the run image sbom - -The accepted media types would be: -* `application/vnd.cyclonedx+json` with ext `cdx.json` -* `application/spdx+json` with ext `spdx.json` -* `application/vnd.syft+json` with ext `syft.json` -* others? +* `my-run-image-sbom.cdx.json` at `/layers/sbom/launch/base-image/sbom.cdx.json`. Note that this would make `base-image` a reserved buildpack ID. + +* An `io.buildpacks.sbom.base` label with the following schema: +```json +{ + "sha": "run-image-layer-diffID", + "formats": [ "" ] +} +``` + +The accepted SBOM media types would be: +* `application/vnd.cyclonedx+json` for files with extension `cdx.json` +* `application/spdx+json` for files with extension `spdx.json` +* `application/vnd.syft+json` for files with extension `syft.json` + +If `-run-image-sbom` is provided as a file: +* The lifecycle will ensure that the file has a supported extension +* The lifecycle will add the appropriate media type to `formats` + +If `-run-image-sbom` is provided as a directory: +* The lifecycle will ensure that all files within the directory have supported extensions +* The lifecycle will add the appropriate media type for each file to `formats` ## Rebase Following the rebase invocation above, the exported app image would contain: -* `my-new-run-image-sbom.json` somewhere in `/layers/sbom` +* `my-new-run-image-sbom.cdx.json` at `/layers/sbom/launch/base-image/sbom.cdx.json` * The layer containing the old run image sbom would be removed -* The `io.buildpacks.sbom.base` label would be updated to contain the diffID of the layer containing the new run image sbom +* The `io.buildpacks.sbom.base` label would be updated to contain the diffID of the layer containing the new run image sbom and to ensure that `formats` is accurate for the new file ## When a run image has an sbom baked in @@ -112,8 +122,7 @@ Why should we *not* do this? Leaving the location of the run image sbom unspec'd [unresolved-questions]: #unresolved-questions - What should be the path of the run image sbom within the image? -- How should the layer containing the run image sbom be designated? This layer containing the buildpack-provided sbom is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. #186 proposed `io.buildpacks.base.sbom` for the layer containing the run image sbom, and `io.buildpacks.app.sbom` for the layer containing the buildpack-provided sbom (in addition to `io.buildpacks.lifecycle.metadata`). -- What should be all the accepted media types / extensions? +- How should the layer containing the run image sbom be designated? This layer containing the buildpack-provided sbom is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. #186 proposed `io.buildpacks.base.sbom` for the layer containing the run image sbom, and `io.buildpacks.app.sbom` for the layer containing the buildpack-provided sbom (in addition to `io.buildpacks.lifecycle.metadata`). Should we "future proof" the label name in case we might eventually want to attach build SBOMs to application images? - What related issues do you consider out of scope for this RFC that could be addressed in the future independently of the solution that comes out of this RFC? - The existence or behavior of a preparer binary that knows how to download run image sboms. From 3b196a6da6d6d2cd2983ded9cd6ca3b6cbc723ca Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 31 Mar 2022 09:47:50 -0400 Subject: [PATCH 09/12] Update label name Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index 07999bcf2..3f11dc3b1 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -48,7 +48,7 @@ Example invocation: Following the build invocation above, the exported app image would contain: * `my-run-image-sbom.cdx.json` at `/layers/sbom/launch/base-image/sbom.cdx.json`. Note that this would make `base-image` a reserved buildpack ID. -* An `io.buildpacks.sbom.base` label with the following schema: +* An `io.buildpacks.base.sbom` label with the following schema: ```json { "sha": "run-image-layer-diffID", @@ -74,20 +74,20 @@ If `-run-image-sbom` is provided as a directory: Following the rebase invocation above, the exported app image would contain: * `my-new-run-image-sbom.cdx.json` at `/layers/sbom/launch/base-image/sbom.cdx.json` * The layer containing the old run image sbom would be removed -* The `io.buildpacks.sbom.base` label would be updated to contain the diffID of the layer containing the new run image sbom and to ensure that `formats` is accurate for the new file +* The `io.buildpacks.base.sbom` label would be updated to contain the diffID of the layer containing the new run image sbom and to ensure that `formats` is accurate for the new file ## When a run image has an sbom baked in -A platform could provide a run image that already has an sbom baked in - i.e., has a layer containing an sbom that is advertised in `io.buildpacks.sbom.base`. In this case, the lifecycle could just do nothing, and the final app image would contain an sbom in the expected location with the expected label. This (as in #186) runs the risk that the sbom baked into the run image has fallen out of date. +A platform could provide a run image that already has an sbom baked in - i.e., has a layer containing an sbom that is advertised in `io.buildpacks.base.sbom`. In this case, the lifecycle could just do nothing, and the final app image would contain an sbom in the expected location with the expected label. This (as in #186) runs the risk that the sbom baked into the run image has fallen out of date. If a platform provided a run image with a baked in sbom and also supplied the `-run-image-sbom` argument, the lifecycle could replace the baked in sbom with the new sbom, much like rebase. ## With Dockerfiles https://github.com/buildpacks/rfcs/pull/173 proposes allowing the run image to be extended or swapped using Dockerfiles. There are a few scenarios that could occur: -* The run image is extended - the lifecycle would need to run a `genpkgs` executable after Dockerfiles have been applied. The result of this invocation would replace the `io.buildpacks.sbom.base` label on the extended run image. In this scenario, the build would proceed according to the process outlined in "When a run image has an sbom baked in". -* The run image is swapped for a new run image that already has a `io.buildpacks.sbom.base` label. In this scenario, the lifecycle would NOT run `genpkgs`, and the build would proceed according to the process outlined in "When a run image has an sbom baked in". -* The run image is swapped for a new run image that does not have a `io.buildpacks.sbom.base` label. In this scenario, there are a couple things that could occur: +* The run image is extended - the lifecycle would need to run a `genpkgs` executable after Dockerfiles have been applied. The result of this invocation would replace the `io.buildpacks.base.sbom` label on the extended run image. In this scenario, the build would proceed according to the process outlined in "When a run image has an sbom baked in". +* The run image is swapped for a new run image that already has a `io.buildpacks.base.sbom` label. In this scenario, the lifecycle would NOT run `genpkgs`, and the build would proceed according to the process outlined in "When a run image has an sbom baked in". +* The run image is swapped for a new run image that does not have a `io.buildpacks.base.sbom` label. In this scenario, there are a couple things that could occur: * The lifecycle could run `genpkgs` to produce a run image sbom for use during export * The lifecycle could return the new run image reference to the platform, expecting the platform to locate an sbom From ad447d2b66e6477ac1de50e60316f18ca1c04a8d Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 31 Mar 2022 10:01:52 -0400 Subject: [PATCH 10/12] Updated to make SBOM formats an outstanding question Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 20 ++++++++------------ 1 file changed, 8 insertions(+), 12 deletions(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index 3f11dc3b1..ad7d30e45 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -48,13 +48,7 @@ Example invocation: Following the build invocation above, the exported app image would contain: * `my-run-image-sbom.cdx.json` at `/layers/sbom/launch/base-image/sbom.cdx.json`. Note that this would make `base-image` a reserved buildpack ID. -* An `io.buildpacks.base.sbom` label with the following schema: -```json -{ - "sha": "run-image-layer-diffID", - "formats": [ "" ] -} -``` +* An `io.buildpacks.base.sbom` label containing the diffID of the layer containing the run image SBOM. The accepted SBOM media types would be: * `application/vnd.cyclonedx+json` for files with extension `cdx.json` @@ -63,18 +57,20 @@ The accepted SBOM media types would be: If `-run-image-sbom` is provided as a file: * The lifecycle will ensure that the file has a supported extension -* The lifecycle will add the appropriate media type to `formats` If `-run-image-sbom` is provided as a directory: * The lifecycle will ensure that all files within the directory have supported extensions -* The lifecycle will add the appropriate media type for each file to `formats` + +## Buildpack-provided SBOMs + +SBOM files output by buildpacks are currently exported in `/layers/sbom/launch/`. The layer containing the buildpack-provided SBOM files is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. For parity with `io.buildpacks.base.sbom`, a `io.buildpacks.app.sbom` label will also be added. ## Rebase Following the rebase invocation above, the exported app image would contain: * `my-new-run-image-sbom.cdx.json` at `/layers/sbom/launch/base-image/sbom.cdx.json` * The layer containing the old run image sbom would be removed -* The `io.buildpacks.base.sbom` label would be updated to contain the diffID of the layer containing the new run image sbom and to ensure that `formats` is accurate for the new file +* The `io.buildpacks.base.sbom` label would be updated to contain the diffID of the layer containing the new run image sbom ## When a run image has an sbom baked in @@ -121,8 +117,8 @@ Why should we *not* do this? Leaving the location of the run image sbom unspec'd # Unresolved Questions [unresolved-questions]: #unresolved-questions -- What should be the path of the run image sbom within the image? -- How should the layer containing the run image sbom be designated? This layer containing the buildpack-provided sbom is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. #186 proposed `io.buildpacks.base.sbom` for the layer containing the run image sbom, and `io.buildpacks.app.sbom` for the layer containing the buildpack-provided sbom (in addition to `io.buildpacks.lifecycle.metadata`). Should we "future proof" the label name in case we might eventually want to attach build SBOMs to application images? +- Should the lifecycle run `genpkgs` if no run image SBOM is provided? +- Do the SBOM formats need to be communicated in a label? - What related issues do you consider out of scope for this RFC that could be addressed in the future independently of the solution that comes out of this RFC? - The existence or behavior of a preparer binary that knows how to download run image sboms. From 1da920c9dcc3fa36e8aabdef68d94edeb2c93b73 Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 31 Mar 2022 12:43:36 -0400 Subject: [PATCH 11/12] Updates following 3/31 Working Group Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 18 ++++++------------ 1 file changed, 6 insertions(+), 12 deletions(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index ad7d30e45..070ee347d 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -63,7 +63,9 @@ If `-run-image-sbom` is provided as a directory: ## Buildpack-provided SBOMs -SBOM files output by buildpacks are currently exported in `/layers/sbom/launch/`. The layer containing the buildpack-provided SBOM files is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. For parity with `io.buildpacks.base.sbom`, a `io.buildpacks.app.sbom` label will also be added. +SBOM files output by buildpacks are currently exported in `/layers/sbom/launch/`, and the diffID of the layer containing the buildpack-provided SBOM files is referenced in the `io.buildpacks.lifecycle.metadata` label with key `sbom`. + +For parity with `io.buildpacks.base.sbom`, a `io.buildpacks.app.sbom` label will also be added containing the diffID of the layer containing the buildpack-provided SBOM files. This will duplicate information but will make the lifecycle implementation easier to manage. ## Rebase @@ -74,18 +76,13 @@ Following the rebase invocation above, the exported app image would contain: ## When a run image has an sbom baked in -A platform could provide a run image that already has an sbom baked in - i.e., has a layer containing an sbom that is advertised in `io.buildpacks.base.sbom`. In this case, the lifecycle could just do nothing, and the final app image would contain an sbom in the expected location with the expected label. This (as in #186) runs the risk that the sbom baked into the run image has fallen out of date. - -If a platform provided a run image with a baked in sbom and also supplied the `-run-image-sbom` argument, the lifecycle could replace the baked in sbom with the new sbom, much like rebase. +Though a platform could theoretically provide a run image that already has an SBOM baked in (i.e., has a layer containing an sbom that is advertised in `io.buildpacks.base.sbom`), this would be discouraged. Platforms should use an industry standard method of associating a run image with an SBOM. ## With Dockerfiles https://github.com/buildpacks/rfcs/pull/173 proposes allowing the run image to be extended or swapped using Dockerfiles. There are a few scenarios that could occur: -* The run image is extended - the lifecycle would need to run a `genpkgs` executable after Dockerfiles have been applied. The result of this invocation would replace the `io.buildpacks.base.sbom` label on the extended run image. In this scenario, the build would proceed according to the process outlined in "When a run image has an sbom baked in". -* The run image is swapped for a new run image that already has a `io.buildpacks.base.sbom` label. In this scenario, the lifecycle would NOT run `genpkgs`, and the build would proceed according to the process outlined in "When a run image has an sbom baked in". -* The run image is swapped for a new run image that does not have a `io.buildpacks.base.sbom` label. In this scenario, there are a couple things that could occur: - * The lifecycle could run `genpkgs` to produce a run image sbom for use during export - * The lifecycle could return the new run image reference to the platform, expecting the platform to locate an sbom +* The run image is extended - the lifecycle would need to run a `genpkgs` executable after Dockerfiles have been applied. The result of this invocation would be provided to the platform so that the platform can provide it as an input to the exporter. +* The run image is swapped for a new run image that already exists. In this scenario, the lifecycle could return the run image reference to the platform, so that the platform could attempt to locate an SBOM. Alternatively, `genpkgs` could be overloaded to first attempt to locate an SBOM and only scan the image if a pre-existing SBOM cannot be found. ## With pack @@ -120,9 +117,6 @@ Why should we *not* do this? Leaving the location of the run image sbom unspec'd - Should the lifecycle run `genpkgs` if no run image SBOM is provided? - Do the SBOM formats need to be communicated in a label? -- What related issues do you consider out of scope for this RFC that could be addressed in the future independently of the solution that comes out of this RFC? - - The existence or behavior of a preparer binary that knows how to download run image sboms. - # Spec. Changes (OPTIONAL) [spec-changes]: #spec-changes Does this RFC entail any proposed changes to the core specifications or extensions? New fields on the exporter and rebaser. A new label on the app image to designate the layer containing the run image sbom. From f6768327641c8daa9d9683870ad312a21ec65c78 Mon Sep 17 00:00:00 2001 From: Natalie Arellano Date: Thu, 31 Mar 2022 12:46:09 -0400 Subject: [PATCH 12/12] Add more questions Signed-off-by: Natalie Arellano --- text/0000-run-image-sbom.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/text/0000-run-image-sbom.md b/text/0000-run-image-sbom.md index 070ee347d..c64f54d52 100644 --- a/text/0000-run-image-sbom.md +++ b/text/0000-run-image-sbom.md @@ -115,7 +115,8 @@ Why should we *not* do this? Leaving the location of the run image sbom unspec'd [unresolved-questions]: #unresolved-questions - Should the lifecycle run `genpkgs` if no run image SBOM is provided? -- Do the SBOM formats need to be communicated in a label? +- Do the available SBOM formats need to be communicated in a label? +- How should `genpkgs` behave? Should it also attempt to locate a pre-existing SBOM? # Spec. Changes (OPTIONAL) [spec-changes]: #spec-changes