build: route releases through OSS Exit Gate (b/515767982) (#25)

Repoint the Cloud Build pipeline at the OSS Exit Gate AR repository so that tag-triggered builds publish via the Exit Gate to PyPI instead of to a private AR repo.

Tyler committed May 26, 2026 at 13:00 UTC 0aa77e522abc824107788e2f7a33826a68cbc219
1 file changed +44 -11
cloudbuild.yaml
+44 -11
@@ -1,8 +1,13 @@
1 # Cloud Build pipeline triggered on git tag push.
2 #
3 -# Builds an sdist + wheel for colab-cli using `uv build`, then publishes both
4 -# to the Artifact Registry Python repository at
5 -# us-central1-python.pkg.dev/colab-cli-external/colab-cli/
3 +# Builds an sdist + wheel for google-colab-cli using `uv build`, then publishes
4 +# both to the OSS Exit Gate Artifact Registry repository:
5 +# https://us-python.pkg.dev/oss-exit-gate-prod/google-colab-cli--pypi
6 +# and triggers an Exit Gate release by uploading a manifest to:
7 +# gs://oss-exit-gate-prod-projects-bucket/google-colab-cli/pypi/manifests/
8 +#
9 +# OSS Exit Gate consumes the artifacts from AR and publishes them to PyPI under
10 +# the google-colab-cli project. See go/oss-exit-gate-release-python.
11 #
12 # The build runs against the tagged commit (TAG_NAME is set by the trigger).
13 # Version is derived from the git tag by hatch-vcs, so the checkout must have
@@ -10,14 +15,17 @@
15 #
16 # Trigger: GitHub push to refs/tags/v* on googlecolab/google-colab-cli (main).
17 substitutions:
13 - _AR_LOCATION: us-central1
14 - _AR_REPOSITORY: colab-cli
15 - _AR_PROJECT: colab-cli-external
18 + _AR_LOCATION: us
19 + _AR_REPOSITORY: google-colab-cli--pypi
20 + _AR_PROJECT: oss-exit-gate-prod
21 + _EG_PROJECT_NAME: google-colab-cli
22 + _EG_REGISTRY: pypi
23 + _EG_TRIGGER_BUCKET: oss-exit-gate-prod-projects-bucket
24
25 steps:
26 # 1. Ensure hatch-vcs sees the tag. Cloud Build's default GitHub checkout
27 # is shallow and may omit tag refs; unshallow + force-fetch tags so
20 - # `git describe` returns the clean tag (e.g. v0.4.0 -> 0.4.0) rather
28 + # `git describe` returns the clean tag (e.g. v0.5.5 -> 0.5.5) rather
29 # than a dev-suffixed pseudo-version.
30 - id: show-version
31 name: gcr.io/cloud-builders/git
@@ -45,10 +53,11 @@ steps:
53 uv build
54 ls -la dist/
55
48 - # 3. Publish artifacts to Artifact Registry via twine + the
56 + # 3. Publish artifacts to the OSS Exit Gate AR repository via twine + the
57 # google-artifactregistry-auth keyring plugin (uses ADC from the
50 - # Cloud Build service account).
51 - - id: publish
58 + # Cloud Build service account, which is registered as a builder in
59 + # the project's project.txtpb).
60 + - id: publish-to-ar
61 name: python:3.13-slim
62 entrypoint: bash
63 args:
@@ -62,10 +71,34 @@ steps:
71 --verbose \
72 dist/*
73
74 + # 4. Trigger the OSS Exit Gate release by uploading a manifest file to the
75 + # project's GCS trigger bucket. `publish_all: true` tells the Exit Gate to
76 + # publish every artifact currently in our AR repo, which is correct here
77 + # because the trigger fires on a single tag push and only the artifacts
78 + # for that tag are in AR at this moment (Exit Gate auto-cleans on success).
79 + #
80 + # Note: this step runs in the same Cloud Build as the AR upload. This is
81 + # fine for BCID L0 (no attestations). When/if we move to BCID L1+ this
82 + # must be split into a separate build that fires after this one succeeds;
83 + # see go/oss-exit-gate-faq#why-manifest.
84 + - id: trigger-release
85 + name: gcr.io/google.com/cloudsdktool/cloud-sdk:slim
86 + entrypoint: bash
87 + args:
88 + - -c
89 + - |
90 + set -e
91 + MANIFEST="${_EG_PROJECT_NAME}-${TAG_NAME}.json"
92 + echo '{"publish_all": true}' > "$${MANIFEST}"
93 + echo "Manifest contents:"
94 + cat "$${MANIFEST}"
95 + gcloud storage cp "$${MANIFEST}" \
96 + "gs://${_EG_TRIGGER_BUCKET}/${_EG_PROJECT_NAME}/${_EG_REGISTRY}/manifests/$${MANIFEST}"
97 +
98 # Surface the built artifacts in the Cloud Build UI / logs.
99 artifacts:
100 objects:
68 - location: gs://${PROJECT_ID}_cloudbuild/colab-cli/${TAG_NAME}
101 + location: gs://${PROJECT_ID}_cloudbuild/google-colab-cli/${TAG_NAME}
102 paths:
103 - dist/*
104