Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
48 changes: 48 additions & 0 deletions .github/workflows/release-crate.yml
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,10 @@ jobs:
name: build + test + publish dry-run
runs-on: ubuntu-latest
steps:
- name: Harden the runner
uses: step-security/harden-runner@9af89fc71515a100421586dfdb3dc9c984fbf411 # v2.19.4
with:
egress-policy: audit
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
- uses: dtolnay/rust-toolchain@29eef336d9b2848a0b548edc03f92a220660cdb8 # stable (2026-03-27)
with:
Expand All @@ -57,6 +61,10 @@ jobs:
contents: read
actions: read
steps:
- name: Harden the runner
uses: step-security/harden-runner@9af89fc71515a100421586dfdb3dc9c984fbf411 # v2.19.4
with:
egress-policy: audit
- name: assert ci.yml is green for this commit
env:
GH_TOKEN: ${{ github.token }}
Expand Down Expand Up @@ -84,11 +92,51 @@ jobs:
permissions:
contents: read
id-token: write
# Required by actions/attest-build-provenance to write the SLSA
# provenance attestation for the published .crate.
attestations: write
steps:
- name: Harden the runner
uses: step-security/harden-runner@9af89fc71515a100421586dfdb3dc9c984fbf411 # v2.19.4
with:
egress-policy: audit
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
- uses: dtolnay/rust-toolchain@29eef336d9b2848a0b548edc03f92a220660cdb8 # stable (2026-03-27)
with:
toolchain: stable
# Supply-chain attestation + SBOM, run BEFORE the publish so a failed
# attestation fails the release closed (the .crate is never pushed if we
# can't attest it). crates.io does not host SBOMs, so the CycloneDX SBOM
# is uploaded as a build artifact rather than shipped with the crate; the
# attestation below is GitHub-issued SLSA build provenance bound to the
# exact published .crate.
- name: Package the crate (produces the artifact to attest)
# Emits target/package/ordvec-<version>.crate — the precise byte-for-byte
# tarball that `cargo publish` uploads, so the provenance covers the
# published artifact.
run: cargo package -p ordvec --locked
- name: Generate CycloneDX SBOM for the crate
# cargo-cyclonedx writes ordvec.cdx.json (named <package>.cdx.json) at the
# repo root for the core crate. Verified locally: the command rejects
# `-p`; package scoping is via --manifest-path against the root manifest,
# which is the `ordvec` package.
run: |
cargo install cargo-cyclonedx --version 0.5.9 --locked
cargo cyclonedx --manifest-path Cargo.toml --format json
Comment thread
Fieldnote-Echo marked this conversation as resolved.
Comment thread
Fieldnote-Echo marked this conversation as resolved.
- name: Attest build provenance for the .crate
uses: actions/attest-build-provenance@a2bbfa25375fe432b6a289bc6b6cd05ecd0c4c32 # v4.1.0
with:
subject-path: target/package/*.crate
- name: Upload SBOM as a build artifact
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
with:
name: sbom-crate
path: ordvec.cdx.json
if-no-files-found: error
# Mint the crates.io OIDC credential LAST — only here, immediately before
# publish, so the short-lived token is never live during the
# `cargo install cargo-cyclonedx` step (third-party code) or the
# attestation/upload steps. Minimises the token's exposure window.
- name: Mint a short-lived crates.io credential (OIDC)
id: auth
uses: rust-lang/crates-io-auth-action@bbd81622f20ce9e2dd9622e3218b975523e45bbe # v1.0.4
Expand Down
45 changes: 45 additions & 0 deletions .github/workflows/release-python.yml
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,10 @@ jobs:
- { runner: macos-latest, target: aarch64, manylinux: auto }
- { runner: windows-latest, target: x64, manylinux: auto }
steps:
- name: Harden the runner
uses: step-security/harden-runner@9af89fc71515a100421586dfdb3dc9c984fbf411 # v2.19.4
with:
egress-policy: audit
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
- name: Build abi3 wheel (covers CPython 3.9+)
uses: PyO3/maturin-action@e83996d129638aa358a18fbd1dfb82f0b0fb5d3b # v1.51.0
Expand Down Expand Up @@ -76,6 +80,10 @@ jobs:
name: sdist
runs-on: ubuntu-latest
steps:
- name: Harden the runner
uses: step-security/harden-runner@9af89fc71515a100421586dfdb3dc9c984fbf411 # v2.19.4
with:
egress-policy: audit
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
- name: Build the sdist
uses: PyO3/maturin-action@e83996d129638aa358a18fbd1dfb82f0b0fb5d3b # v1.51.0
Expand Down Expand Up @@ -107,6 +115,24 @@ jobs:
with:
name: sdist
path: ordvec-python/dist
# CycloneDX SBOM — generated ONCE here, not per-wheel. The wheel is the
# compiled Rust extension, so the binding crate's Cargo dependency tree is
# the meaningful, platform-independent bill of materials. cargo-cyclonedx
# walks the manifest and writes `<crate>.cdx.json` next to it, i.e.
# `ordvec-python/ordvec-python.cdx.json`. The dtolnay toolchain above
# provides cargo.
- name: Install cargo-cyclonedx
shell: bash
run: cargo install cargo-cyclonedx --version 0.5.9 --locked
- name: Generate CycloneDX SBOM for the binding crate
shell: bash
run: cargo cyclonedx --manifest-path ordvec-python/Cargo.toml --format json
Comment thread
Fieldnote-Echo marked this conversation as resolved.
- name: Upload the SBOM
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
with:
name: sbom-python
path: ordvec-python/ordvec-python.cdx.json
Comment thread
Fieldnote-Echo marked this conversation as resolved.
Comment thread
Fieldnote-Echo marked this conversation as resolved.
if-no-files-found: error

require-ci-green:
# The wheel must not ship from a commit whose core (`ci.yml`) or binding
Expand All @@ -120,6 +146,10 @@ jobs:
contents: read
actions: read
steps:
- name: Harden the runner
uses: step-security/harden-runner@9af89fc71515a100421586dfdb3dc9c984fbf411 # v2.19.4
with:
egress-policy: audit
- name: assert ci.yml and python.yml are green for this commit
env:
GH_TOKEN: ${{ github.token }}
Expand Down Expand Up @@ -151,10 +181,25 @@ jobs:
permissions:
contents: read
id-token: write
attestations: write
steps:
- name: Harden the runner
uses: step-security/harden-runner@9af89fc71515a100421586dfdb3dc9c984fbf411 # v2.19.4
with:
egress-policy: audit
- uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1
with:
path: dist
merge-multiple: true
# GitHub SLSA build provenance for the wheels + sdist, complementary to the
# PyPI-side PEP 740 attestations the pypa publish step emits below. Attest
# runs BEFORE publish so a failed attestation fails the release closed —
# nothing is pushed to PyPI without provenance recorded first.
- name: Attest build provenance for the wheels + sdist
uses: actions/attest-build-provenance@a2bbfa25375fe432b6a289bc6b6cd05ecd0c4c32 # v4.1.0
with:
subject-path: |
dist/*.whl
dist/*.tar.gz
- name: Publish to PyPI (Trusted Publishing; PEP 740 attestations on by default)
uses: pypa/gh-action-pypi-publish@cef221092ed1bacb1cc03d23a2d87d1d172e277b # v1.14.0
Loading