From efa6bed460b3e15c8c46141cb20e25ac469aed93 Mon Sep 17 00:00:00 2001 From: Codex Date: Sat, 20 Jun 2026 22:38:34 +0000 Subject: [PATCH] fix(agentrun): retry registry manifest visibility --- scripts/src/agentrun.ts | 25 +++++++++++++++++++++++-- 1 file changed, 23 insertions(+), 2 deletions(-) diff --git a/scripts/src/agentrun.ts b/scripts/src/agentrun.ts index 085957cc..65ecd6cd 100644 --- a/scripts/src/agentrun.ts +++ b/scripts/src/agentrun.ts @@ -3701,9 +3701,30 @@ function yamlLaneBuildImageSubmitScript(spec: AgentRunLaneSpec, sourceCommit: st "$build_arg_values", "EOF", " if docker image inspect \"$image\" >/dev/null 2>&1; then build_status=reused; else docker build $args -f \"$containerfile\" -t \"$image\" \"$context_dir\"; build_status=built; fi", + " manifest_accept='application/vnd.oci.image.index.v1+json, application/vnd.oci.image.manifest.v1+json, application/vnd.docker.distribution.manifest.v2+json'", + " fetch_manifest_digest() {", + " ref=\"$1\"", + " attempt=1", + " max_attempts=30", + " while [ \"$attempt\" -le \"$max_attempts\" ]; do", + " headers=$(mktemp)", + " if curl -fsSI -H \"Accept: $manifest_accept\" \"http://127.0.0.1:5000/v2/${image_repository#127.0.0.1:5000/}/manifests/$ref\" >\"$headers\"; then", + " found_digest=$(awk -F': ' 'tolower($1)==\"docker-content-digest\"{print $2}' \"$headers\" | tr -d '\\r' | head -n 1)", + " rm -f \"$headers\"", + " if [ -n \"$found_digest\" ]; then printf '%s' \"$found_digest\"; return 0; fi", + " else", + " rm -f \"$headers\"", + " fi", + " printf '{\"event\":\"agentrun-registry-manifest-probe\",\"status\":\"retrying\",\"ref\":\"%s\",\"attempt\":\"%s/%s\"}\\n' \"$ref\" \"$attempt\" \"$max_attempts\" >&2", + " sleep 1", + " attempt=$((attempt + 1))", + " done", + " printf '{\"event\":\"agentrun-registry-manifest-probe\",\"status\":\"exhausted\",\"ref\":\"%s\",\"attempt\":\"%s/%s\"}\\n' \"$ref\" \"$max_attempts\" \"$max_attempts\" >&2", + " return 1", + " }", " docker push \"$image\"", - " digest=$(docker inspect --format='{{index .RepoDigests 0}}' \"$image\" 2>/dev/null | sed 's/^.*@//' || true)", - " if [ -z \"$digest\" ]; then digest=$(curl -fsSI -H 'Accept: application/vnd.docker.distribution.manifest.v2+json' \"http://127.0.0.1:5000/v2/${image_repository#127.0.0.1:5000/}/manifests/$env_identity\" 2>/dev/null | awk -F': ' 'tolower($1)==\"docker-content-digest\"{print $2}' | tr -d '\\r' | head -n 1 || true); fi", + " digest=$(fetch_manifest_digest \"$env_identity\" || true)", + " if [ -n \"$digest\" ]; then verified_digest=$(fetch_manifest_digest \"$digest\" || true); if [ \"$verified_digest\" != \"$digest\" ]; then digest=; fi; fi", " STATUS=\"$build_status\" DIGEST=\"$digest\" JOB_ID=\"$job_id\" SOURCE_COMMIT=\"$source_commit\" ENV_IDENTITY=\"$env_identity\" IMAGE_REPOSITORY=\"$image_repository\" node <<'NODE' > \"$status_file\"", "const digest = process.env.DIGEST || null;", "console.log(JSON.stringify({ ok: Boolean(digest), status: process.env.STATUS || 'built', jobId: process.env.JOB_ID, sourceCommit: process.env.SOURCE_COMMIT, envIdentity: process.env.ENV_IDENTITY, image: `${process.env.IMAGE_REPOSITORY}:${process.env.ENV_IDENTITY}`, digest, repositoryDigest: digest ? `${process.env.IMAGE_REPOSITORY}@${digest}` : null, valuesPrinted: false }));",