Skip to content

fix(build, stapel, import): stop imports failing with sbom enabled - #470

Merged
reyreavman merged 1 commit into
mainfrom
fix/build/sbom-import-network
Oct 26, 2026
Merged

reyreavman merged 1 commit into
mainfrom
fix/build/sbom-import-network

Conversation

@reyreavman

@reyreavman reyreavman commented Oct 23, 2026 •

Copy link
Copy Markdown
Collaborator

Summary

A stapel image with import: fails to build under build.sbom.enable: true with the Docker backend: the dependencies* stage dies with rsync: failed to connect to <import-server ip>: Network unreachable (101), is retried once "in a clean container after a transport failure" and fails again with container run failed: exit code 10. Repro from a clean checkout:

project: demo
configVersion: 1
build:
  sbom:
    enable: true
    standard: cyclonedx@1.6
---
image: donor
from: alpine:3.20
---
image: app
from: alpine:3.20
import:
- image: donor
  add: /etc/os-release
  to: /donor/os-release
  before: install
WERF_BUILDAH_MODE=docker werf build

What

  • Under build.sbom.enable: true with the Docker backend the dependencies* (import) stages run with the backend's default network again and the import completes; previously they ran with --network=none.
  • Shell stages (beforeInstall, install, beforeSetup, setup) still run with --network=none under build.sbom.enable: true, and --backend-network / werf.yaml network: still cannot open them.
  • The packages stage is unchanged: it keeps the network it had.
  • build.sbom.enable: false is unchanged: no stage gets a network override.
  • The "Network is disabled for shell stages" warning is unchanged.
  • Stage digests are unchanged, so already built stages are reused.

Why

With build.sbom.enable: true the isolation code marks every stage except packages as network-less, dependencies* included. Until 09f22e7 that mark never reached the import container: only BaseStage.PrepareImage applied it and DependenciesStage.PrepareImage bypasses that path, so the write was dead and imports worked. 09f22e7 made the build phase forward a stage's own network override into the builder for every stage — to keep the sign stages closed against --backend-network — which turned the dead write live. Under the Docker backend an import is an rsync from the import-server container over the bridge network, so a network-less import stage cannot succeed.

Leaving the import stage network-less buys nothing for the SBOM: the stage carries no shell: commands and copies files out of an image that import: already declares and whose BOM the importing image already inherits. Marking the dependencies* stages as needing network, the way packages already is, keeps shell stages offline and lets imports work.

Rejected: special-casing the import stages inside the build phase's option merge — the exemption belongs where packages is exempted, so one rule decides which stages the SBOM isolation leaves alone.

Fixes: 09f22e7 ("feat(build, stapel): sign files inside the image with a key the build container never sees")

@reyreavman

reyreavman commented Oct 23, 2026 •

Copy link
Copy Markdown
Collaborator Author

Verification

  • task test:e2e paths=./test/e2e/sbom labelFilter=pip parallel=1 -- -focus="marks a package of the donor" (Docker backend, Linux host with kind registry): fails on main with the rsync Network unreachable (101) transport error, passes with this branch — 1 of 75 specs, 98 s.
  • task test:e2e paths=./test/e2e/build labelFilter=managed-deps parallel=1 (Docker backend, same host): both specs pass — sbom.enable=true still enforces --network=none on shell stages, sbom.enable=false still does not.
  • Mutation: reverted newDependenciesStage to pass the base options through unchanged → DependenciesStage needs network regardless of the base options fails for all four stage names, and all four entries of network isolation under build.sbom.enable fail on the import stage's network expecting empty, getting none.

Review focus

  • The exemption is decided by NeedsNetwork(), the same predicate the SBOM isolation already uses for packages; confirm no other consumer of that predicate gives the import stage something beyond skipping the override.

With build.sbom.enable: true the SBOM network isolation marks every stage
except packages as network-less, the dependencies* stages that carry
import: included. Until 09f22e7 ("feat(build, stapel): sign files
inside the image with a key the build container never sees") that mark
never reached the import container: only BaseStage.PrepareImage applied
it, and DependenciesStage.PrepareImage bypasses it. stageBuildOptions
now forwards the stage's network override into the builder for every
stage, so the import container started with --network=none. Under the
Docker backend an import is an rsync from the import-server container
over the bridge network, so the stage failed with "rsync: failed to
connect ... Network unreachable (101)" and the build stopped.

Mark the dependencies stages as needing network, exactly as the packages
stage already is, so the SBOM isolation skips them. The stage carries no
shell: commands and copies files out of an image that import: already
declares and the SBOM already accounts for, so shell stages stay offline
and the guarantee is unchanged.

Signed-off-by: Radmir Khurum <radmir.khurum@flant.com>
@reyreavman
reyreavman force-pushed the fix/build/sbom-import-network branch from 1869480 to ba8d6ef Compare October 23, 2026 10:08
@reyreavman
reyreavman marked this pull request as ready for review October 26, 2026 07:29
@reyreavman
reyreavman merged commit 478b751 into main Oct 26, 2026
37 of 40 checks passed
@reyreavman
reyreavman deleted the fix/build/sbom-import-network branch October 26, 2026 07:29
reyreavman pushed a commit that referenced this pull request Oct 26, 2026
🤖 I have created a release *beep* *boop*
---


##
[3.12.0-dk.3](v3.12.0-dk.2...v3.12.0-dk.3)
(2026-10-26)


### Features

* **build, stapel:** sign files matched by a glob pattern
([#471](#471))
([ffda24e](ffda24e))
* **sbom:** inventory installed Python, JavaScript and Lua packages
([#472](#472))
([7fde219](7fde219))


### Bug Fixes

* **build, stapel, import:** stop imports failing with sbom enabled
([#470](#470))
([478b751](478b751))
* **sbom:** avoid marking editable Python packages as absent
([#474](#474))
([e0b4b66](e0b4b66))
* **sbom:** retain legacy Python bytecode after source removal
([#476](#476))
([36debcb](36debcb))
* **sbom:** stop marking os-pm packages under /lib64 as not shipped
([#475](#475))
([cd0a029](cd0a029))

---
This PR was generated with [Release
Please](https://github.com/googleapis/release-please). See
[documentation](https://github.com/googleapis/release-please#release-please).
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant