From 9306e8ad55f73e4fd9c9559d11f8455cbe325bd3 Mon Sep 17 00:00:00 2001 From: Copybara Date: Sun, 20 Sep 2026 06:11:39 +0000 Subject: [PATCH 1/4] Project import generated by Copybara. FolderOrigin-RevId: b31318e06ac415532fa16ad18652f8fb1fced134 --- .repository-projection.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.repository-projection.json b/.repository-projection.json index 9a48dec..dd916e0 100644 --- a/.repository-projection.json +++ b/.repository-projection.json @@ -3,9 +3,9 @@ "projection": "private-runner", "projectionSchemaVersion": 1, "sourceRepository": "dx-corp/mono", - "sourceSha": "3acc63c2c655c22b5ca7f2d55b63a6b87eced2bc", + "sourceSha": "b31318e06ac415532fa16ad18652f8fb1fced134", "destinationRepository": "dx-corp/private-runner", - "priorProjectedBase": "4c59b136d1b9abc96c418ce667fbd0e698b34179", + "priorProjectedBase": "fc47ef254c76a9f9411f68b03afa5940be505d34", "definitionDigest": "851a6bbb3b1c4baf8c69cb244ea18da79c272bf0f9f21aaf5525836c960f2f7b", "toolDigest": "c8000985e1bd708bf1f8754b27cc1a2aad67af10ee23cf5317bd1fba670b4456", "contentDigest": "be8bd7addc2c1fd81c6a26c08e037b6adcb31c2bbd5ee63f468fe86889578d51", From c02581c4b4a9cb8dcc1ccdd00e99e92e1e716831 Mon Sep 17 00:00:00 2001 From: Copybara Date: Sun, 20 Sep 2026 20:34:14 +0000 Subject: [PATCH 2/4] Project import generated by Copybara. FolderOrigin-RevId: 8420a1f8c5fdd07a3d2d4d2a46e0db0bb6bbb352 --- .repository-projection.json | 8 ++-- scripts/distribution-validation.mjs | 61 +++++++++++++++++++++++++++-- 2 files changed, 62 insertions(+), 7 deletions(-) diff --git a/.repository-projection.json b/.repository-projection.json index dd916e0..7e036a1 100644 --- a/.repository-projection.json +++ b/.repository-projection.json @@ -3,11 +3,11 @@ "projection": "private-runner", "projectionSchemaVersion": 1, "sourceRepository": "dx-corp/mono", - "sourceSha": "b31318e06ac415532fa16ad18652f8fb1fced134", + "sourceSha": "8420a1f8c5fdd07a3d2d4d2a46e0db0bb6bbb352", "destinationRepository": "dx-corp/private-runner", - "priorProjectedBase": "fc47ef254c76a9f9411f68b03afa5940be505d34", + "priorProjectedBase": "2155ddaa3e138affb9e5f5bb3b838f64c35c7c9e", "definitionDigest": "851a6bbb3b1c4baf8c69cb244ea18da79c272bf0f9f21aaf5525836c960f2f7b", - "toolDigest": "c8000985e1bd708bf1f8754b27cc1a2aad67af10ee23cf5317bd1fba670b4456", - "contentDigest": "be8bd7addc2c1fd81c6a26c08e037b6adcb31c2bbd5ee63f468fe86889578d51", + "toolDigest": "de718162d050963e0c04ca9cbc0e38b1db545e838e587f949bcd9fd8aded6bcd", + "contentDigest": "edf6b57621edb4c66ea290b872d90b1f8790dcb4006955d10c7f91d127f290a2", "publicationEligible": true } diff --git a/scripts/distribution-validation.mjs b/scripts/distribution-validation.mjs index 9cc6486..84a0515 100644 --- a/scripts/distribution-validation.mjs +++ b/scripts/distribution-validation.mjs @@ -6,9 +6,20 @@ import { join, relative, resolve } from "node:path"; import { pathToFileURL } from "node:url"; import { parseArgs } from "node:util"; -const NAMES = new Set(["endpoint", "private-runner", "private-deployment", "api", "examples", "plugins"]); +const NAMES = new Set(["endpoint", "private-runner", "private-deployment", "api", "examples", "plugins", "capobara"]); const SHA = /^[0-9a-f]{40}$/; const HEX = /^[0-9a-f]{64}$/; +// `toolDigest` is the one provenance field with two legitimate shapes. Node +// hashes the contents of its own TOOL_INPUTS script list, giving a 64-hex +// SHA-256; Capobara embeds the git tree id of `rust/tools/capobara`, giving a +// 40-hex object name. Both are valid "the tool that ran this matches the tool +// committed at this revision" proofs, and the Rust side's +// `git::is_tree_id_or_digest` accepts both widths for exactly this reason -- +// this predicate is its twin and must stay in step with it. A receipt written +// by either implementation has to validate here, or a clone of +// `dx-corp/capobara` fails `invalid provenance toolDigest` against a +// perfectly correct tree. +const TOOL_DIGEST = /^(?:[0-9a-f]{40}|[0-9a-f]{64})$/; const PROTO = [ "common/v1/analytics.proto", "common/v1/authz.proto", "common/v1/classification.proto", "common/v1/delivery.proto", "common/v1/entity.proto", "common/v1/risk.proto", "common/v1/surface.proto", @@ -82,7 +93,8 @@ export async function validateProvenance(name, root) { requireValue(provenance.projection === name && provenance.sourceRepository === "dx-corp/mono" && provenance.destinationRepository === `dx-corp/${name}`, "projection provenance identity mismatch"); requireValue(SHA.test(provenance.sourceSha) && SHA.test(provenance.priorProjectedBase), "projection SHAs are invalid"); - for (const key of ["definitionDigest", "toolDigest", "contentDigest"]) requireValue(HEX.test(provenance[key]), `invalid provenance ${key}`); + for (const key of ["definitionDigest", "contentDigest"]) requireValue(HEX.test(provenance[key]), `invalid provenance ${key}`); + requireValue(TOOL_DIGEST.test(provenance.toolDigest), "invalid provenance toolDigest"); requireValue(typeof provenance.publicationEligible === "boolean", "invalid publication eligibility"); return provenance; } @@ -244,6 +256,49 @@ async function validatePlugins(root, files) { for (const path of files) requireValue(!/(?:prompt-audit|session-history|product-kit)/i.test(path), `private plugin surface: ${path}`); } +// `capobara` is admitted here rather than routed around this validation by +// the workflow's `matrix.name == 'capobara'` condition. That condition only +// governs the `sync` job; `node scripts/projections/verify-catalog.mjs +// --validate` -- the `repository-projections` component's own CI gate -- +// builds and validates *every* catalog entry, and `validate.mjs` admits any +// name the catalog holds, so a catalog entry with no validator here fails +// that gate on `unsupported distribution: capobara`. +// +// The compile proof for the projected crate lives in the crate's own +// `tests/standalone_build.rs`, which copies it out of the workspace and runs +// `cargo build --locked`. Repeating that here would add a full dependency +// build to every catalog verification, so this checks the standalone +// closure without compiling: the manifest, the crate-root lockfile and the +// single-package workspace that the projection has to produce, plus the +// internal surfaces it must not carry. +async function validateCapobara(root, files) { + for (const required of ["Cargo.toml", "Cargo.lock", "README.md", "build.rs", "src/main.rs", "src/lib.rs"]) { + requireValue(files.includes(required), `capobara is missing ${required}`); + } + for (const path of files) { + requireValue(!/^scripts\//.test(path), `capobara contains an internal surface: ${path}`); + requireValue(!/^tests\/fixtures\/definitions\//.test(path), `capobara contains an excluded fixture: ${path}`); + } + const manifest = await readFile(join(root, "Cargo.toml"), "utf8"); + requireValue(!/\bworkspace\s*=\s*true/.test(manifest), "capobara Cargo.toml still inherits from the Mono workspace"); + // Resolution must include dependencies here: with `--no-deps` nothing is + // resolved, so `--locked` has nothing to compare and a stale lockfile + // passes. With the full graph, `--locked` fails when the projected + // crate-root lockfile does not match the projected manifest, which is the + // failure this projection is most exposed to -- the standalone lockfile is + // generated separately from the workspace one and can go stale without any + // Mono build noticing. + // + // This resolves all 178 locked packages, so on a cold runner it fetches the + // crates.io index and downloads every `.crate`. That is a network-dependent + // step in the component's CI gate; the component already declares `rust` in + // `ci.test.tools`, and nothing cheaper discriminates (see above). + const metadata = JSON.parse(run("cargo", ["metadata", "--locked", "--format-version", "1"], root)); + requireValue(metadata.workspace_members.length === 1, "capobara standalone workspace gained a member"); + const member = metadata.packages.find(pkg => pkg.id === metadata.workspace_members[0]); + requireValue(member?.name === "capobara", "capobara standalone workspace member is not the crate"); +} + export async function validateDistribution({ name, target }) { requireValue(NAMES.has(name), `unsupported distribution: ${name}`); const root = resolve(target); @@ -252,7 +307,7 @@ export async function validateDistribution({ name, target }) { await validateProvenance(name, root); const validators = { endpoint: validateEndpoint, "private-runner": validateRunner, "private-deployment": validateDeployment, - api: validateApi, examples: validateExamples, plugins: validatePlugins, + api: validateApi, examples: validateExamples, plugins: validatePlugins, capobara: validateCapobara, }; await validators[name](root, files); return { name, target: root, files: files.length, valid: true }; From 56cf0b23451e0ccd4715ab8ee0bddb300dd402cf Mon Sep 17 00:00:00 2001 From: dx-corp projector Date: Sun, 20 Sep 2026 21:25:48 +0000 Subject: [PATCH 3/4] chore: project private-runner from Mono a2e8b231b208 --- .repository-projection.json | 8 ++++---- scripts/distribution-validation.mjs | 20 ++++++++++---------- 2 files changed, 14 insertions(+), 14 deletions(-) diff --git a/.repository-projection.json b/.repository-projection.json index 7e036a1..d096342 100644 --- a/.repository-projection.json +++ b/.repository-projection.json @@ -3,11 +3,11 @@ "projection": "private-runner", "projectionSchemaVersion": 1, "sourceRepository": "dx-corp/mono", - "sourceSha": "8420a1f8c5fdd07a3d2d4d2a46e0db0bb6bbb352", + "sourceSha": "a2e8b231b208f9e30b0a115eb132176e1e7c301a", "destinationRepository": "dx-corp/private-runner", - "priorProjectedBase": "2155ddaa3e138affb9e5f5bb3b838f64c35c7c9e", + "priorProjectedBase": "ea992bb2c82071cba13c128c73d67402fa9a3095", "definitionDigest": "851a6bbb3b1c4baf8c69cb244ea18da79c272bf0f9f21aaf5525836c960f2f7b", - "toolDigest": "de718162d050963e0c04ca9cbc0e38b1db545e838e587f949bcd9fd8aded6bcd", - "contentDigest": "edf6b57621edb4c66ea290b872d90b1f8790dcb4006955d10c7f91d127f290a2", + "toolDigest": "8a4412f3a379ca0bd1cfea9bff69cc46773c6d1f", + "contentDigest": "7df5e7b61415b5b8fc2e8118fd195fcc30ec44ab87d58fad49a22bb72a141c26", "publicationEligible": true } diff --git a/scripts/distribution-validation.mjs b/scripts/distribution-validation.mjs index 84a0515..13c5b1b 100644 --- a/scripts/distribution-validation.mjs +++ b/scripts/distribution-validation.mjs @@ -21,10 +21,12 @@ const HEX = /^[0-9a-f]{64}$/; // perfectly correct tree. const TOOL_DIGEST = /^(?:[0-9a-f]{40}|[0-9a-f]{64})$/; const PROTO = [ + "agentruntime/v1/runtime.proto", "agents/v1/agents.proto", "codex/v1/codex.proto", "common/v1/analytics.proto", "common/v1/authz.proto", "common/v1/classification.proto", - "common/v1/delivery.proto", "common/v1/entity.proto", "common/v1/risk.proto", "common/v1/surface.proto", - "connectors/v1/connectors.proto", "console/v1/console.proto", "deixic/v1/deixic.proto", - "memory/v1/memory.proto", "meter/v1/meter.proto", "orbcontrol/v1/orb_control.proto", + "common/v1/delivery.proto", "common/v1/entity.proto", "common/v1/risk.proto", + "common/v1/surface.proto", "connectors/v1/connectors.proto", "console/v1/console.proto", + "deixic/v1/deixic.proto", "memory/v1/memory.proto", "meter/v1/meter.proto", + "objectives/v1/objectives.proto", "orbcontrol/v1/orb_control.proto", "platform/v1/platform.proto", "remoterunner/v1/remoterunner.proto", "toolexecution/v1/toolexecution.proto", "traces/v1/traces.proto", "vfs/v1/filesystem.proto", ].sort(); @@ -256,13 +258,11 @@ async function validatePlugins(root, files) { for (const path of files) requireValue(!/(?:prompt-audit|session-history|product-kit)/i.test(path), `private plugin surface: ${path}`); } -// `capobara` is admitted here rather than routed around this validation by -// the workflow's `matrix.name == 'capobara'` condition. That condition only -// governs the `sync` job; `node scripts/projections/verify-catalog.mjs -// --validate` -- the `repository-projections` component's own CI gate -- -// builds and validates *every* catalog entry, and `validate.mjs` admits any -// name the catalog holds, so a catalog entry with no validator here fails -// that gate on `unsupported distribution: capobara`. +// `capobara` is admitted here like every other catalog entry: `validate.mjs` +// admits any name the catalog holds, and the `sync` job validates every +// prepared projection between Capobara's dry run and its real run, so a +// catalog entry with no validator here fails its publication on +// `unsupported distribution: capobara`. // // The compile proof for the projected crate lives in the crate's own // `tests/standalone_build.rs`, which copies it out of the workspace and runs From 7040d9e9661a4c1e26af5da2f693c0e76f329253 Mon Sep 17 00:00:00 2001 From: dx-corp projector Date: Mon, 21 Sep 2026 00:28:24 +0000 Subject: [PATCH 4/4] chore: project private-runner from Mono 9b559bc70e7d --- .repository-projection.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.repository-projection.json b/.repository-projection.json index d096342..148a2d4 100644 --- a/.repository-projection.json +++ b/.repository-projection.json @@ -3,9 +3,9 @@ "projection": "private-runner", "projectionSchemaVersion": 1, "sourceRepository": "dx-corp/mono", - "sourceSha": "a2e8b231b208f9e30b0a115eb132176e1e7c301a", + "sourceSha": "9b559bc70e7d8afc723d2ac67c8c62fe0cfbdeeb", "destinationRepository": "dx-corp/private-runner", - "priorProjectedBase": "ea992bb2c82071cba13c128c73d67402fa9a3095", + "priorProjectedBase": "50dab1abbd91fd3281a525d09b16651b796e2a1a", "definitionDigest": "851a6bbb3b1c4baf8c69cb244ea18da79c272bf0f9f21aaf5525836c960f2f7b", "toolDigest": "8a4412f3a379ca0bd1cfea9bff69cc46773c6d1f", "contentDigest": "7df5e7b61415b5b8fc2e8118fd195fcc30ec44ab87d58fad49a22bb72a141c26",