CI / Tests, lint (push) Successful in 11s
Checked against netork's first signed images (main-142912c): cosign verify on the tag succeeds, verify-attestation on it finds only the signature, because BuildKit pushes even one platform as an index with its provenance manifest. The CIS result and SBOM are on the linux/amd64 image.
97 lines
4.2 KiB
Markdown
97 lines
4.2 KiB
Markdown
# image-tools
|
|
|
|
Judges, signs and verifies the container images of [netOrk](https://git.netork.io/NetOrk/netork).
|
|
Every image repository of NetOrk uses these tools at a pinned commit, so the same rules apply
|
|
to every link of the chain:
|
|
|
|
```
|
|
netork/base-os ──► netork/base-python ──► netork/engine, netork/satellite
|
|
└─► netork/ui
|
|
└─► postgres, valkey, signal-api, apt-cacher-ng, unbound
|
|
```
|
|
|
|
Each link checks the signature of the image it builds on, is judged against CIS, and is signed
|
|
with its CIS result and SBOM attached (NetOrk/netork#1390).
|
|
|
|
## What it does
|
|
|
|
| | |
|
|
|---|---|
|
|
| **CIS gate** (`image_tools/cis.py`) | CIS Docker Benchmark 1.6.0 §4 and the CIS Debian Linux 12 controls that make sense in a container. Trivy measures what it automates; `image_tools/cis_os.sh` measures from inside the image. The image's repository decides the rest in its `cis.toml` and names the packages it may hold in `packages.allow`. |
|
|
| **SBOM** (`image_tools/sbom.py`) | The image's CycloneDX SBOM, as Trivy reads it. |
|
|
| **Signature** (`bin/sign.sh`) | A cosign signature on the reference and on every platform image behind it, with the CIS result and the SBOM as in-toto attestations. Nothing goes to a public transparency log. |
|
|
| **Verification** (`bin/verify-base.sh`, `bin/verify-signature.sh`) | Every `FROM` image of a Dockerfile is pinned by digest and signed with the key in `cosign.pub`. |
|
|
| **Verdict** (`image_tools/verify.py`) | Whether a rebuild improves on the pinned image, by netOrk's matcher (kb-server), for a base's nightly. |
|
|
| **Bump** (`image_tools/bump.py`) | One pull request in every repository of a `dependents.toml` that moves only the pin, and that repository's workflow started. |
|
|
|
|
## Using it in a workflow
|
|
|
|
```yaml
|
|
- name: Verify the base images
|
|
uses: https://git.netork.io/NetOrk/image-tools/actions/verify-base@<commit>
|
|
with:
|
|
dockerfiles: docker/engine/Dockerfile
|
|
|
|
# build the image, then:
|
|
- name: Judge it
|
|
uses: https://git.netork.io/NetOrk/image-tools/actions/judge@<commit>
|
|
with:
|
|
image: registry.netork.io/netork/engine:main-abc1234
|
|
arch: amd64
|
|
|
|
# a base's nightly, to decide whether its pin moves:
|
|
- name: Judge it against the pin
|
|
id: verdict
|
|
uses: https://git.netork.io/NetOrk/image-tools/actions/verdict@<commit>
|
|
env:
|
|
NETORK_LICENSE_KEY: ${{ secrets.NETORK_LICENSE_KEY }}
|
|
with:
|
|
current: registry.netork.io/netork/base-os:pinned
|
|
candidate: registry.netork.io/netork/base-os:13-20261022.3-amd64
|
|
|
|
# push it, then:
|
|
- name: Sign it
|
|
uses: https://git.netork.io/NetOrk/image-tools/actions/sign@<commit>
|
|
env:
|
|
COSIGN_PRIVATE_KEY_B64: ${{ secrets.COSIGN_PRIVATE_KEY_B64 }}
|
|
COSIGN_PASSWORD: ${{ secrets.COSIGN_PASSWORD }}
|
|
with:
|
|
ref: registry.netork.io/netork/engine@sha256:…
|
|
```
|
|
|
|
The judge action reads `cis.toml` and `packages.allow` from the working directory by default.
|
|
The runner needs Docker, Python 3.11 or newer, and `curl`; cosign is installed by the actions,
|
|
pinned and checked against its release checksum (`bin/install-cosign.sh`).
|
|
|
|
## Verifying an image yourself
|
|
|
|
```bash
|
|
# The signature, on the tag or digest you pull (an index is signed with every image in it):
|
|
cosign verify --key cosign.pub --insecure-ignore-tlog registry.netork.io/netork/engine:latest-dev
|
|
|
|
# The CIS result and the SBOM belong to each platform image, not to the index around it:
|
|
docker buildx imagetools inspect registry.netork.io/netork/engine:latest-dev # the linux/amd64 digest
|
|
cosign verify-attestation --key cosign.pub --insecure-ignore-tlog \
|
|
--type https://netork.io/attestations/cis/v1 registry.netork.io/netork/engine@sha256:<platform digest>
|
|
cosign verify-attestation --key cosign.pub --insecure-ignore-tlog \
|
|
--type cyclonedx registry.netork.io/netork/engine@sha256:<platform digest>
|
|
```
|
|
|
|
Even a single-platform image is pushed as an index: BuildKit adds its provenance manifest.
|
|
|
|
`cosign.pub` is the public half of the `COSIGN_PRIVATE_KEY_B64` organization secret. The private
|
|
key comes base64 in one line: the runner masks a secret only where it appears whole.
|
|
|
|
## Development
|
|
|
|
```bash
|
|
pip install pytest ruff pyyaml shellcheck-py
|
|
pytest -q
|
|
ruff format --check . && ruff check .
|
|
shellcheck bin/*.sh image_tools/cis_os.sh
|
|
```
|
|
|
|
## License
|
|
|
|
MIT, see [LICENSE](LICENSE).
|