Your browser sucks, JavaScript disabled! Gunnar's console needs JavaScript and WebAssembly. Git over SSH on port 2222 does not.

nordisk/holger

build-space/src/lib.rs

//! # holger-build-space
//!
//! Holger's **build-space as data**, the consumer side of nornir's build-thing. The
//! declaration is `holger-recipe`'s Rust code ([`holger_recipe::declared`]); this crate
//! answers from it, projects it onto a [`BuildSurface`] a UI renders, and drives a row
//! through nornir's one [`assemble`] seam (validate, build, content-hash, attest, emit
//! build-info lineage).
//!
//! The rows are ONE product list (lane HOL-PRODUCTS): the four products, each its
//! `cargo install` line (`holger`, `holger-downstream`, `holger-cli`, `holger-ui`), and
//! what only an estate needs (the static appliance and metered servers, the front, the
//! signed wasm plugins, the installer media). Each row declares its linkage (`fat` /
//! `thin`) and each role names its normal case with `default = true`.
//!
//! ```
//! let set = holger_build_space::build_variant_set().unwrap();
//! assert_eq!(set.names(), vec!["holger", "holger-downstream", "holger-cli", "holger-ui", "mvp-server-musl", "mvp-server-metered", "mvp-server-musl-metered", "mvp-server-musl-metered-narrate", "holger-mvp-appliance", "holger-installer", "holger-installer-metered", "holger-appliance-iso", "plugin-allocation", "plugin-skidbladnir", "plugin-rust-toolchain", "estate-front-musl-metered", "estate-front-musl-metered-narrate", "holger-front-installer-metered", "holger-keep", "holger-front-keep", "downstream-musl", "holger-downstream-oneway-installer", "downstream-fetch-musl", "holger-downstream-installer"]);
//! // Every role names exactly one normal case.
//! assert!(set.check_defaults().is_empty());
//! ```

use std::path::{Path, PathBuf};

use anyhow::Result;
use nornir_build_thing::{
    assemble, Assemble, AssembleCtx, Assembled, Attestation, BuildInfoRow, BuildInfoSink,
    BuildProvenance, BuildSurface, BuildVariantSet, Builders, HostInfo, InMemBuildInfoSink,
    Outcome, Toolchain,
};

/// The repo label stamped into the surface + provenance records.
pub const REPO: &str = "holger";

/// Holger's declared build-space as a typed [`BuildVariantSet`] — answered from
/// the CODE ([`holger_recipe::declared`]), the one declaration.
///
/// Until 0.2.0 this parsed an `include_str!` of a crate-local byte-copy of the
/// hand-written `.nornir/build-variants.toml` — the reverse of the law (code →
/// toml). The toml is now EMITTED by `cargo run -p holger-build-thing -- emit`
/// and held to the code by that crate's `toml_parity` test; nothing here reads it.
///
/// Stays `Result` so every existing caller keeps compiling unchanged.
pub fn build_variant_set() -> Result<BuildVariantSet> {
    Ok(holger_recipe::declared())
}

/// Project holger's build-space onto the data-driven [`BuildSurface`] a UI renders
/// (one row per variant, each with its materialized `cargo` command, validity, and a
/// Build action).
pub fn build_surface() -> Result<BuildSurface> {
    Ok(BuildSurface::from_set(REPO, &build_variant_set()?))
}

/// **Press the build-thing button** for one declared tier: validate the tier
/// against holger's build-space, then capture a content-addressed
/// build-provenance [`Attestation`] describing what building it produced.
///
/// This is holger *consuming* nornir-build-thing's provenance path. It is the
/// dep-light describe/attest half — it does **not** itself shell out to cargo;
/// the caller passes the `artifacts` a build already emitted (their paths under
/// `repo_root`) and whether that build succeeded. The record binds the exact
/// tier descriptor (verbatim), the materialized `cargo` argv + resolved feature/
/// profile/target axes, the VCS rev + working-tree freshness of `repo_root`, the
/// detected [`Toolchain`], the [`HostInfo`] (cores + memory), the outcome, and
/// the SHA-256 of every artifact — then folds it to a stable digest.
///
/// The heavy end-to-end path (dispatch on the tier's kind, spawn `cargo build`,
/// hash the produced executables, attest + emit build-info lineage in one shot) is
/// [`assemble_tier`] / [`build_tier`] over [`nornir_build_thing::assemble`], which
/// the nornir Build tab and `nornir build --variant <tier>` also drive.
/// `press_tier` is the seam a test or an offline tool uses to attest an artifact
/// built out of band.
///
/// The returned attestation is **unsealed** — `is_sealed()` is `false`. holger
/// never fabricates a signature; the real seal is znippy's detached-CMS signer,
/// applied via [`Attestation::seal_with`] behind nornir's `build-provenance`
/// feature.
pub fn press_tier(
    name: &str,
    repo_root: &Path,
    outcome: Outcome,
    artifacts: &[PathBuf],
) -> Result<Attestation> {
    let set = build_variant_set()?;
    let variant = set.require(name)?;
    set.validate(variant)?;
    BuildProvenance::capture(
        variant,
        REPO,
        repo_root,
        Toolchain::detect(),
        HostInfo::detect(),
        outcome,
        artifacts,
    )?
    .attest()
}

/// **Press the build-thing button END TO END through the unified `assemble()`
/// seam** (nornir-build-thing design §f7) for one declared tier.
///
/// This REPLACES the former hand-rolled `build_and_press` (which shelled the
/// per-tier `cargo` argv itself via `build_variant`). A chosen tier now flows
/// through nornir's ONE polymorphic entry point,
/// [`nornir_build_thing::assemble`]: it validates the tier, **dispatches on its
/// [`ArtifactKind`](nornir_build_thing::ArtifactKind)** — a product is an `exe`, the
/// sold server a `service`, and both lower to the SAME cargo builder — actually builds
/// it, content-hashes the produced artifact(s), and emits the per-row **build-info
/// lineage** (`provenance` / `dep` / `artifact` rows, each artifact row carrying its
/// `content_id`) to `info`. It returns ONE content-addressed [`Assembled`] receipt
/// binding the produced output, the proof, and that lineage.
///
/// Where [`press_tier`] attests a PRE-BUILT artifact the caller supplies (the
/// dep-light describe/attest seam), `assemble_tier` is the real "press the button":
/// build THEN attest, in one shot. `builders` is the injected builder seam — the
/// production [`Builders::new`] for the real cargo-only path, or a fake in tests;
/// `exec_dir` is where the built binary / service lands (the `BinaryArtifact` /
/// `ServiceSpec` install path). Unknown tiers reject UP FRONT (via
/// [`BuildVariantSet::require`]) before any build, with the same tier-listing
/// message [`press_tier`] gives.
///
/// The receipt's proof is **unsealed** — holger never fabricates a signature.
pub fn assemble_tier(
    name: &str,
    repo_root: &Path,
    exec_dir: &Path,
    info: &dyn BuildInfoSink,
    builders: &dyn Assemble,
) -> Result<Assembled> {
    let set = build_variant_set()?;
    // Up-front rejection with the tier-listing message, before any build work.
    let variant = set.require(name)?.clone();
    let mut ctx = AssembleCtx::new(repo_root, exec_dir, info, builders);
    ctx.repo = REPO.to_string();
    assemble(&set, &variant, &ctx)
}

/// The real cargo-only [`assemble_tier`]: build the tier through
/// [`nornir_build_thing::assemble`] with the production [`Builders`] (the cargo
/// builder; no image / vm), landing binaries under `<repo_root>/target/release`,
/// and collect the per-tier build-info lineage in-process. Returns the
/// [`Assembled`] receipt AND the captured [`BuildInfoRow`] lineage.
///
/// This is what `cargo run -p xtask build --variant <tier>` drives — holger's
/// first-party equivalent of `nornir build --variant <tier>`. It is **heavy and
/// opt-in**: `assemble` spawns `cargo`, so a `release` tier build can take minutes.
pub fn build_tier(name: &str, repo_root: &Path) -> Result<(Assembled, Vec<BuildInfoRow>)> {
    let exec_dir = repo_root.join("target").join("release");
    let sink = InMemBuildInfoSink::new();
    let assembled = assemble_tier(name, repo_root, &exec_dir, &sink, &Builders::new())?;
    Ok((assembled, sink.rows()))
}

#[cfg(test)]
mod tests {
    use super::*;

    const NAMES: [&str; 24] = [
        "holger",
        "holger-downstream",
        "holger-cli",
        "holger-ui",
        "mvp-server-musl",
        "mvp-server-metered",
        "mvp-server-musl-metered",
        "mvp-server-musl-metered-narrate",
        "holger-mvp-appliance",
        "holger-installer",
        "holger-installer-metered",
        "holger-appliance-iso",
        "plugin-allocation",
        "plugin-skidbladnir",
        "plugin-rust-toolchain",
        "estate-front-musl-metered",
        "estate-front-musl-metered-narrate",
        "holger-front-installer-metered",
        "holger-keep",
        "holger-front-keep",
        "downstream-musl",
        "holger-downstream-oneway-installer",
        "downstream-fetch-musl",
        "holger-downstream-installer",
    ];

    /// The descriptor enumerates the one product list, in declaration order, and every
    /// role names its normal case.
    #[test]
    fn enumerates_the_one_product_list() {
        let set = build_variant_set().expect("parse holger build-space");
        assert_eq!(set.names(), NAMES.to_vec());
        assert!(
            set.check_defaults().is_empty(),
            "{:?}",
            set.check_defaults()
        );
        // Coverage law: record the declaration as a test-matrix cell (reuse edda's
        // emitter; no-op unless the `testmatrix` feature is on).
        #[cfg(feature = "testmatrix")]
        nornir_testmatrix::functional_status(
            "holger-build-space",
            "one_product_list_declared",
            set.names() == NAMES.to_vec() && set.check_defaults().is_empty(),
            "the four products + the estate's builds, each role naming its default",
        );
    }

    /// Each product row builds its own crate's one bin with its defaults; the estate's
    /// builds of the server are the same crate with their own feature sets.
    #[test]
    fn each_row_has_the_right_target_and_feature_combo() {
        let set = build_variant_set().unwrap();
        for p in ["holger", "holger-downstream", "holger-cli", "holger-ui"] {
            let v = set.get(p).unwrap_or_else(|| panic!("no product row {p}"));
            assert_eq!(v.package.as_deref(), Some(p), "{p}");
            assert_eq!(v.bin.as_deref(), Some(p), "{p}");
            assert!(
                v.features.is_empty() && !v.no_default_features,
                "{p}: `cargo install {p}`, its defaults"
            );
        }
        // The static appliance: the server crate, its own feature set, cross-built for musl.
        let musl = set.get("mvp-server-musl").expect("the appliance row");
        assert_eq!(musl.package.as_deref(), Some("holger"));
        assert_eq!(musl.bin.as_deref(), Some("holger-mvp"));
        assert!(musl.no_default_features);
        assert_eq!(musl.target.as_deref(), Some("x86_64-unknown-linux-musl"));
        for f in [
            "mvp-server",
            "appliance",
            "paired",
            "auth-passkey",
            "sign",
            "allow-meter",
        ] {
            assert!(
                musl.features.iter().any(|x| x == f),
                "mvp-server-musl names `{f}`: {:?}",
                musl.features
            );
        }
        // The sold server: the paid door and its own bin.
        let sold = set.get("mvp-server-metered").expect("the sold row");
        assert_eq!(sold.bin.as_deref(), Some("holger-mvp-metered"));
        assert!(sold.features.iter().any(|x| x == "metered"));
    }

    /// No row group is mutually exclusive any more (the extras are features of the same
    /// crates), and each estate bin requires its marker feature.
    #[test]
    fn no_exclusive_group_and_the_estate_bins_require_their_marker() {
        let set = build_variant_set().unwrap();
        assert!(set.exclusive.is_empty(), "{:?}", set.exclusive);
        assert_eq!(
            set.required.get("holger-mvp").map(Vec::as_slice),
            Some(&["mvp-server".to_string()][..])
        );
        assert_eq!(
            set.required.get("holger-mvp-metered").map(Vec::as_slice),
            Some(&["mvp-server".to_string(), "metered".to_string()][..])
        );
        assert_eq!(set.required.len(), 2, "{:?}", set.required);
    }

    /// Every feature a row enables is one holger actually OFFERS, and every declared
    /// variant validates against the set's rules (config-time sanity).
    #[test]
    fn every_row_validates_against_the_offered_feature_universe() {
        let set = build_variant_set().unwrap();
        for f in [
            "sign",
            "testmatrix",
            "served",
            "front",
            "all-formats",
            "online",
            "federation",
            "full",
        ] {
            assert!(
                set.offers.contains(f),
                "holger offers the real feature '{f}'"
            );
        }
        assert!(
            !set.offers.contains("gui"),
            "`gui` is holger-egui's, not holger's"
        );
        set.validate_all().expect("every row is internally valid");
    }

    /// The materialized cargo command lines are the argv nornir would run.
    #[test]
    fn rows_materialize_the_expected_cargo_commands() {
        let set = build_variant_set().unwrap();
        let holger = set.get("holger").unwrap().command_line();
        assert!(
            holger.starts_with("cargo build -p holger --bin holger"),
            "{holger}"
        );
        assert!(
            !holger.contains("--features") && !holger.contains("--no-default-features"),
            "the product is its defaults: {holger}"
        );
        let musl = set.get("mvp-server-musl").unwrap().command_line();
        for want in [
            "-p holger",
            "--bin holger-mvp",
            "--no-default-features",
            "--target x86_64-unknown-linux-musl",
            "--profile release",
        ] {
            assert!(musl.contains(want), "{want} missing: {musl}");
        }
    }

    /// The reflected surface is what a UI renders: one row per declared variant, all
    /// valid, each with a `nornir build --variant <name>` action. The count is the row
    /// count: every media cell is claimed by a pointer variant of the same name.
    #[test]
    fn surface_reflects_valid_rows_with_build_actions() {
        let surface = build_surface().unwrap();
        assert_eq!(surface.repo, REPO);
        assert_eq!(surface.variant_names(), NAMES.to_vec());
        assert_eq!(surface.variants.len(), NAMES.len());
        assert!(
            surface.variants.iter().all(|v| v.valid),
            "no invalid variant"
        );
        for (v, row) in surface.variants.iter().zip(surface.variant_names()) {
            assert_eq!(v.build_action.cli, format!("nornir build --variant {row}"));
        }
        let j = surface.state_json();
        assert_eq!(j["surface"], "build");
        assert_eq!(j["variant_count"], NAMES.len());
        assert_eq!(j["valid_count"], NAMES.len());
    }

    use nornir_build_thing::{
        ArtifactKind, BuildOutcome, BuildProvenanceSink, JsonFileSink, PROVENANCE_SCHEMA,
    };

    /// A **fake cargo builder** for the `assemble()` seam: instead of shelling
    /// `cargo`, it synthesizes a deterministic artifact file (`target/release/<bin>`,
    /// bytes `ARTIFACT <tier>`) and captures REAL build-provenance over it — so the
    /// whole `assemble` dispatch + content-hash + build-info lineage machinery runs
    /// with no toolchain. Container / VM kinds are never reached (the rows driven here are
    /// all cargo kinds).
    struct FakeCargo;
    impl Assemble for FakeCargo {
        fn build_cargo(
            &self,
            set: &BuildVariantSet,
            name: &str,
            repo_root: &Path,
            _sink: &dyn BuildInfoSink,
        ) -> Result<BuildOutcome> {
            let v = set.require(name)?.clone();
            let dir = repo_root.join("target/release");
            std::fs::create_dir_all(&dir)?;
            let bin = v
                .bin
                .clone()
                .or_else(|| v.package.clone())
                .unwrap_or_else(|| v.name.clone());
            let art = dir.join(&bin);
            std::fs::write(&art, format!("ARTIFACT {name}"))?;
            let rec = BuildProvenance::capture(
                &v,
                REPO,
                repo_root,
                Toolchain {
                    rustc: "rustc 1.85.0".into(),
                    host: "x86_64-unknown-linux-gnu".into(),
                    cargo: "cargo 1.85.0".into(),
                    // `Toolchain` grew `image`/`image_sha256` (edda f0aff77) so a
                    // provenance record can name WHICH container built an
                    // artifact. This is a fake build in a test double, so it ran
                    // in no container and claims none.
                    ..Default::default()
                },
                HostInfo {
                    cores: 8,
                    memory_bytes: 0,
                },
                Outcome::Success,
                std::slice::from_ref(&art),
            )?;
            Ok(BuildOutcome {
                variant: name.to_string(),
                artifacts: vec![art],
                attestation: rec.attest()?,
                success: true,
            })
        }
    }

    /// **RED-WHEN-BROKEN — the rows validate + produce their artifacts via
    /// `assemble()`.** Each is driven through the unified f7 [`assemble`] seam (with a
    /// fake cargo builder, no toolchain): it must validate, dispatch on its declared
    /// [`ArtifactKind`] (a product → `exe`, the sold server → `service`), produce a
    /// content-addressed artifact, and emit a build-info lineage carrying provenance +
    /// artifact rows. A `kind` out of coherence with its `embeds`/`member` is rejected
    /// by `assemble`'s config gate and this test goes RED.
    #[test]
    fn rows_validate_and_assemble_produce_artifacts() {
        let dir = tempfile::tempdir().unwrap();
        let root = dir.path();
        let exec = Path::new("/usr/local/bin");
        let sink = InMemBuildInfoSink::new();
        let fake = FakeCargo;

        for (tier, kind) in [
            ("holger", ArtifactKind::Exe),
            ("holger-downstream", ArtifactKind::Exe),
            ("mvp-server-metered", ArtifactKind::Service),
        ] {
            let a = assemble_tier(tier, root, exec, &sink, &fake)
                .unwrap_or_else(|e| panic!("assemble tier '{tier}': {e:#}"));

            // Dispatched on the declared kind — output + proof both agree.
            assert_eq!(a.kind(), kind, "{tier}: output.kind() is the declared kind");
            assert_eq!(a.attestation.kind(), kind, "{tier}: proof kind matches");

            // Produced a content-addressed artifact.
            assert!(
                !a.artifact_content_ids().is_empty(),
                "{tier}: assemble produced an artifact with a content_id"
            );

            // The build-info lineage carries the record ABOUT the build.
            assert!(
                a.lineage.iter().any(|r| r.kind == "provenance"),
                "{tier}: lineage has provenance rows"
            );
            assert!(
                a.lineage
                    .iter()
                    .any(|r| r.kind == "artifact" && !r.content_id.is_empty()),
                "{tier}: lineage has a content-addressed artifact row"
            );

            // Content-addressed digest holds; unsealed (holger never fakes a seal).
            assert!(
                a.attestation.digest_matches_record().unwrap(),
                "{tier}: digest verifies"
            );
            assert!(!a.attestation.is_sealed(), "{tier}: unsealed");
        }

        // Coverage law: record the assemble verdict as a test-matrix cell.
        #[cfg(feature = "testmatrix")]
        nornir_testmatrix::functional_status(
            "holger-build-space",
            "rows_assemble",
            true,
            "holger(exe) · holger-downstream(exe) · mvp-server-metered(service) validate + assemble() → artifacts + lineage",
        );
    }

    /// A throw-away "repo" holding one fake produced artifact under
    /// `target/release/<bin>`, so provenance capture can content-hash a real file
    /// without a heavy release build.
    fn fake_build(bin: &str, bytes: &[u8]) -> (tempfile::TempDir, PathBuf) {
        let dir = tempfile::tempdir().expect("tempdir");
        let out = dir.path().join("target/release");
        std::fs::create_dir_all(&out).unwrap();
        let art = out.join(bin);
        std::fs::write(&art, bytes).unwrap();
        (dir, art)
    }

    /// Pressing the `holger` row captures a provenance attestation that binds the
    /// row descriptor + materialized argv + the artifact's content hash, folds to a
    /// stable digest, is unsealed (holger never fakes a signature), and round-trips
    /// through JSON with its digest intact.
    #[test]
    fn press_holger_row_captures_and_round_trips_provenance() {
        let (dir, art) = fake_build("holger", b"ELF holger bytes");
        let att = press_tier("holger", dir.path(), Outcome::Success, &[art])
            .expect("press the holger row");

        // WHAT: the verbatim `holger` row descriptor rode into the record.
        assert_eq!(att.record.schema, PROVENANCE_SCHEMA);
        assert_eq!(att.record.repo, REPO);
        assert_eq!(att.record.variant.name, "holger");
        assert_eq!(att.record.variant.package.as_deref(), Some("holger"));
        assert_eq!(att.record.variant.bin.as_deref(), Some("holger"));

        // INPUTS: the materialized argv matches the row's own cargo_args.
        let row = build_variant_set().unwrap().get("holger").unwrap().clone();
        assert_eq!(att.record.inputs.cargo_args, row.cargo_args());
        assert_eq!(att.record.inputs.profile, "release");
        assert_eq!(att.record.outcome, Outcome::Success);

        // HOST: cores are probed (>=1 on any real machine).
        assert!(att.record.host.cores >= 1, "host cores were probed");

        // HASHES: the produced artifact is content-addressed + sized.
        assert_eq!(att.record.artifacts.len(), 1);
        let a = &att.record.artifacts[0];
        assert_eq!(a.path, "target/release/holger");
        assert_eq!(a.bytes, b"ELF holger bytes".len() as u64);

        // SEAL: unsealed, but the digest verifies against the record.
        assert!(!att.is_sealed(), "holger never fabricates a seal");
        assert!(att.digest_matches_record().unwrap());

        // ROUND-TRIP: JSON out → in preserves the digest and it still verifies.
        let back = Attestation::from_json(&att.to_json().unwrap()).unwrap();
        assert_eq!(back.digest, att.digest);
        assert!(back.digest_matches_record().unwrap());
    }

    /// The captured record persists to a dep-light `JsonFileSink` ledger and
    /// reloads as a full, re-parseable provenance entry — the warehouse-ledger
    /// seam a leaf repo uses without nornir's Iceberg stack.
    #[test]
    fn pressed_record_persists_to_a_reloadable_ledger() {
        let (dir, art) = fake_build("holger-downstream", b"downstream bytes");
        let att = press_tier("holger-downstream", dir.path(), Outcome::Success, &[art]).unwrap();

        let ledger_dir = tempfile::tempdir().unwrap();
        let sink = JsonFileSink::new(ledger_dir.path());
        sink.record(&att.record).unwrap();
        sink.record(&att.record).unwrap();

        let text = std::fs::read_to_string(sink.path()).unwrap();
        assert_eq!(text.lines().count(), 2, "one JSON line per record");
        let first = BuildProvenance::from_json(text.lines().next().unwrap()).unwrap();
        assert_eq!(first.repo, REPO);
        assert_eq!(first.variant.name, "holger-downstream");
    }

    /// Pressing a row holger doesn't declare is rejected up front, naming the real rows.
    #[test]
    fn pressing_an_unknown_tier_is_rejected() {
        let err = press_tier("turbo", Path::new("."), Outcome::Success, &[])
            .expect_err("unknown tier must reject");
        let msg = err.to_string();
        assert!(msg.contains("no build variant 'turbo'"), "{msg}");
        assert!(
            msg.contains("holger-downstream") && msg.contains("mvp-server-musl"),
            "lists rows: {msg}"
        );
    }

    /// The end-to-end [`assemble_tier`] rejects an unknown tier UP FRONT (via
    /// `require`) with the exact same message [`press_tier`] gives — proving the
    /// validation happens BEFORE any build, and the injected builder is never
    /// invoked (no `target/` dir is created).
    #[test]
    fn assemble_tier_rejects_unknown_tier_before_building() {
        let dir = tempfile::tempdir().unwrap();
        let sink = InMemBuildInfoSink::new();
        let fake = FakeCargo;
        let err = assemble_tier("turbo", dir.path(), Path::new("/usr/bin"), &sink, &fake)
            .expect_err("unknown tier must reject before building");
        let msg = err.to_string();
        assert!(msg.contains("no build variant 'turbo'"), "{msg}");
        assert!(
            msg.contains("holger-downstream") && msg.contains("mvp-server-musl"),
            "lists rows: {msg}"
        );

        // Same up-front rejection message as the dep-light describe/attest seam.
        let press_err = press_tier("turbo", Path::new("."), Outcome::Success, &[])
            .expect_err("press_tier also rejects");
        assert_eq!(
            msg,
            press_err.to_string(),
            "same rejection message as press_tier"
        );

        // The fake builder was never reached — no build artifacts materialized.
        assert!(
            !dir.path().join("target").exists(),
            "no build happened for an unknown tier"
        );
    }

    /// HEAVY end-to-end: actually build the `holger-downstream` row THROUGH
    /// `assemble()` against the real holger workspace, hash the produced binary, and
    /// attest it. Ignored by default because `assemble` shells `cargo build` (minutes on
    /// a cold cache).
    ///
    /// Run it explicitly from the workspace root:
    /// ```text
    /// cargo test -p holger-build-space -- --ignored assemble_the_downstream_row_builds_and_attests
    /// ```
    #[test]
    #[ignore = "heavy: assemble() shells `cargo build` for the holger-downstream row against the real workspace"]
    fn assemble_the_downstream_row_builds_and_attests() {
        // Repo root = the workspace dir above build-space/.
        let repo_root = Path::new(env!("CARGO_MANIFEST_DIR"))
            .parent()
            .expect("build-space has a parent (workspace root)")
            .to_path_buf();

        let (assembled, lineage) = build_tier("holger-downstream", &repo_root)
            .expect("build + assemble the holger-downstream row");

        // The product is declared an `exe` kind — dispatch proves it.
        assert_eq!(
            assembled.kind(),
            ArtifactKind::Exe,
            "holger-downstream is an exe"
        );
        assert_eq!(assembled.attestation.kind(), ArtifactKind::Exe);

        // The produced binary was discovered + content-hashed into the lineage.
        assert!(
            !assembled.artifact_content_ids().is_empty(),
            "assemble produced a content-addressed artifact"
        );
        assert!(
            lineage
                .iter()
                .any(|r| r.kind == "artifact" && !r.content_id.is_empty()),
            "the build-info lineage carries a content-addressed artifact row"
        );

        // Content-addressed digest holds, and holger never fabricates a seal.
        assert!(
            assembled.attestation.digest_matches_record().unwrap(),
            "digest verifies against the record"
        );
        assert!(
            !assembled.attestation.is_sealed(),
            "holger never fabricates a seal"
        );
    }

    /// Workspace root = the dir above `build-space/`.
    fn workspace_root() -> PathBuf {
        Path::new(env!("CARGO_MANIFEST_DIR"))
            .parent()
            .expect("build-space has a parent (workspace root)")
            .to_path_buf()
    }

    /// Resolve the exact `cargo tree` dependency closure (`-e no-dev`, no dev-deps)
    /// for `package` built with `features` and `no_default_features`.
    /// Returns the full tree text so a test can assert a crate's presence/absence.
    /// Pure metadata resolution — cargo does NOT compile anything, so this is fast
    /// and box-safe (Law #8: no heavy build here).
    fn cli_closure(package: &str, features: &str, no_default_features: bool) -> String {
        let mut args = vec!["tree".to_string()];
        // `holger-downstream` is a workspace of its own (its rows' `manifest_dir`).
        if package == holger_recipe::variants::DOWNSTREAM {
            args.extend([
                "--manifest-path".to_string(),
                format!(
                    "{}/Cargo.toml",
                    holger_recipe::variants::DOWNSTREAM_MANIFEST_DIR
                ),
            ]);
        }
        args.extend([
            "-p".to_string(),
            package.to_string(),
            "-e".to_string(),
            "no-dev".to_string(),
        ]);
        if !features.is_empty() {
            args.extend(["--features".to_string(), features.to_string()]);
        }
        if no_default_features {
            args.push("--no-default-features".to_string());
        }
        let out = std::process::Command::new(env!("CARGO"))
            .args(&args)
            .current_dir(workspace_root())
            .output()
            .expect("run `cargo tree`");
        assert!(
            out.status.success(),
            "cargo tree ({features}) failed: {}",
            String::from_utf8_lossy(&out.stderr)
        );
        String::from_utf8_lossy(&out.stdout).into_owned()
    }

    /// Every Rust outbound-HTTP client crate an airgap tier is forbidden to link.
    /// `reqwest`/`ureq` are holger's actual egress paths today (OIDC `/userinfo` +
    /// `jwks_uri`, the `bench` GET-bombardment driver, and the `rust-remote`
    /// pull-through upstream); the rest are the other well-known Rust HTTP clients,
    /// denied so a FUTURE re-introduction of egress via a *different* client is
    /// caught red-handed too — the zero-egress guarantee must not hinge on the one
    /// client name holger happens to use now. `hyper`/`tonic`/`h2` are deliberately
    /// ABSENT from this list: they are the INBOUND gRPC *serve* stack (every tier
    /// legitimately links them), not an outbound client.
    const FORBIDDEN_OUTBOUND_CLIENTS: &[&str] = &[
        "reqwest",
        "ureq",
        "isahc",
        "curl",
        "surf",
        "attohttpc",
        "awc",
        "http-client",
    ];

    /// AIRGAP KEYSTONE — provably zero-egress. The server and the downstream with their
    /// defaults (`cargo install holger`, `cargo install holger-downstream`) link NO
    /// outbound HTTP client ([`FORBIDDEN_OUTBOUND_CLIENTS`]). `--features full` DOES link
    /// reqwest + ureq, which proves the test discriminates rather than trivially passing.
    /// Runs `cargo tree` — a metadata resolve, no compile.
    #[test]
    fn the_products_link_no_outbound_http_client() {
        for package in ["holger", "holger-downstream"] {
            let tree = cli_closure(package, "", false);
            for client in FORBIDDEN_OUTBOUND_CLIENTS {
                // Match `<crate> v` so a crate merely NAMED after one can't cause a
                // false positive; cargo-tree prints `name vX.Y`.
                assert!(
                    !tree.contains(&format!("{client} v")),
                    "`cargo install {package}` MUST NOT link outbound HTTP client '{client}' \
                     (zero-egress), but the cargo-tree closure contains it:\n{tree}"
                );
            }
        }
        let full = cli_closure("holger", "full", false);
        assert!(
            full.contains("reqwest v"),
            "`--features full` is the online server and MUST link reqwest:\n{full}"
        );
        assert!(
            full.contains("ureq v"),
            "`--features full` MUST link ureq:\n{full}"
        );

        // Coverage law: record the zero-egress verdict as a test-matrix cell.
        #[cfg(feature = "testmatrix")]
        nornir_testmatrix::functional_status(
            "holger-build-space",
            "products_zero_egress",
            true,
            "holger/holger-downstream link no outbound HTTP client; --features full links reqwest+ureq",
        );
    }

    /// Tampering with a pressed record after the fact breaks its digest — the
    /// content-addressed provenance is a real integrity check.
    #[test]
    fn tampering_a_pressed_record_breaks_the_digest() {
        let (dir, art) = fake_build("holger", b"holger bytes");
        let mut att = press_tier("holger", dir.path(), Outcome::Success, &[art]).unwrap();
        assert!(att.digest_matches_record().unwrap());
        att.record.inputs.vcs_rev = "0".repeat(40);
        assert!(
            !att.digest_matches_record().unwrap(),
            "mutation invalidates the digest"
        );
    }
}