From c4398513cbbfe00734a390e8646aabea526c95dc Mon Sep 17 00:00:00 2001 From: chrischristiansen-glitch Date: Sat, 23 May 2026 23:08:43 +0200 Subject: [PATCH] =?UTF-8?q?feat:=20migrate=20Cloud=20Build=20trigger=20to?= =?UTF-8?q?=202nd=20gen=20(cloudbuildv2=20connection=20=E2=80=94=20no=20ma?= =?UTF-8?q?nual=20OAuth)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- infrastructure/06-cicd-setup.sh | 89 ++++++++++++++++++++++++++------- 1 file changed, 70 insertions(+), 19 deletions(-) diff --git a/infrastructure/06-cicd-setup.sh b/infrastructure/06-cicd-setup.sh index 8ec0844..2761e71 100644 --- a/infrastructure/06-cicd-setup.sh +++ b/infrastructure/06-cicd-setup.sh @@ -1,7 +1,8 @@ #!/usr/bin/env bash -# 06-cicd-setup.sh — Set up Cloud Build trigger + Artifact Registry for CI/CD -# Prerequisites: GitHub repo connected to Cloud Build via GCP Console FIRST: -# https://console.cloud.google.com/cloud-build/triggers/connect +# 06-cicd-setup.sh — Cloud Build 2nd gen: programmatic GitHub connection + trigger +# No manual OAuth in GCP Console required. +# Prerequisites: GitHub PAT stored in Secret Manager as 'github-token' +# gcloud secrets create github-token --data-file=<(echo -n "ghp_YOUR_TOKEN") # Source .env before running: source .env set -euo pipefail @@ -12,19 +13,24 @@ set -euo pipefail : "${ARTIFACT_REPO:?Set ARTIFACT_REPO}" : "${CLOUD_RUN_SERVICE:?Set CLOUD_RUN_SERVICE}" +CONNECTION_NAME="osvauco-github-connection" +TRIGGER_NAME="${CLOUD_RUN_SERVICE}-main-trigger" BRANCH_PATTERN="^main$" +GITHUB_TOKEN_SECRET="github-token" -echo "=== 06: CI/CD Setup for ${PROJECT_ID} ===" +echo "=== 06: CI/CD Setup (2nd gen) for ${PROJECT_ID} ===" bash "$(dirname "$0")/00-authcheck.sh" gcloud services enable \ cloudbuild.googleapis.com \ + cloudbuildv2.googleapis.com \ artifactregistry.googleapis.com \ run.googleapis.com \ + secretmanager.googleapis.com \ --project="${PROJECT_ID}" --quiet -# Create Artifact Registry repo (idempotent) +# --- Artifact Registry (idempotent) --- if ! gcloud artifacts repositories describe "${ARTIFACT_REPO}" \ --location="${REGION}" --project="${PROJECT_ID}" >/dev/null 2>&1; then gcloud artifacts repositories create "${ARTIFACT_REPO}" \ @@ -35,10 +41,9 @@ if ! gcloud artifacts repositories describe "${ARTIFACT_REPO}" \ else echo "✓ Artifact Registry repo already exists" fi - gcloud auth configure-docker "${REGION}-docker.pkg.dev" --quiet -# Grant Cloud Build SA permissions +# --- IAM for Cloud Build SA --- PROJECT_NUMBER=$(gcloud projects describe "${PROJECT_ID}" --format="value(projectNumber)") CB_SA="${PROJECT_NUMBER}@cloudbuild.gserviceaccount.com" @@ -52,29 +57,75 @@ for ROLE in \ done echo "✓ Cloud Build SA IAM bindings applied" -# Create Cloud Build trigger -TRIGGER_NAME="${CLOUD_RUN_SERVICE}-main-trigger" -EXISTING=$(gcloud builds triggers list \ +# --- Grant Cloud Build SA access to GitHub token secret --- +gcloud secrets add-iam-policy-binding "${GITHUB_TOKEN_SECRET}" \ + --project="${PROJECT_ID}" \ + --member="serviceAccount:${CB_SA}" \ + --role="roles/secretmanager.secretAccessor" --quiet +echo "✓ Cloud Build SA granted access to secret: ${GITHUB_TOKEN_SECRET}" + +# --- Cloud Build 2nd gen: Host Connection (idempotent) --- +EXISTING_CONN=$(gcloud builds connections list \ + --region="${REGION}" --project="${PROJECT_ID}" \ + --format="value(name)" 2>/dev/null \ + | grep -c "${CONNECTION_NAME}" || true) + +if [[ "${EXISTING_CONN}" == "0" ]]; then + gcloud builds connections create github "${CONNECTION_NAME}" \ + --authorizer-token-secret-version="projects/${PROJECT_ID}/secrets/${GITHUB_TOKEN_SECRET}/versions/latest" \ + --app-installation-id="${GITHUB_APP_INSTALLATION_ID:-}" \ + --region="${REGION}" \ + --project="${PROJECT_ID}" --quiet + echo "✓ 2nd gen GitHub connection created: ${CONNECTION_NAME}" +else + echo "✓ 2nd gen GitHub connection already exists: ${CONNECTION_NAME}" +fi + +# --- Cloud Build 2nd gen: Repository Link (idempotent) --- +REPO_RESOURCE="projects/${PROJECT_ID}/locations/${REGION}/connections/${CONNECTION_NAME}/repositories/${GITHUB_REPO}" +EXISTING_REPO=$(gcloud builds repositories list \ + --connection="${CONNECTION_NAME}" \ + --region="${REGION}" --project="${PROJECT_ID}" \ + --format="value(name)" 2>/dev/null \ + | grep -c "${GITHUB_REPO}" || true) + +if [[ "${EXISTING_REPO}" == "0" ]]; then + gcloud builds repositories create "${GITHUB_REPO}" \ + --remote-uri="https://github.com/${GITHUB_OWNER}/${GITHUB_REPO}.git" \ + --connection="${CONNECTION_NAME}" \ + --region="${REGION}" \ + --project="${PROJECT_ID}" --quiet + echo "✓ Repository linked: ${GITHUB_OWNER}/${GITHUB_REPO}" +else + echo "✓ Repository already linked" +fi + +# --- Cloud Build Trigger (2nd gen, idempotent) --- +EXISTING_TRIGGER=$(gcloud builds triggers list \ --filter="name=${TRIGGER_NAME}" \ --format="value(name)" 2>/dev/null | head -1 || true) -if [[ -z "${EXISTING}" ]]; then +if [[ -z "${EXISTING_TRIGGER}" ]]; then gcloud builds triggers create github \ --name="${TRIGGER_NAME}" \ - --repo-owner="${GITHUB_OWNER}" \ - --repo-name="${GITHUB_REPO}" \ + --repository="projects/${PROJECT_ID}/locations/${REGION}/connections/${CONNECTION_NAME}/repositories/${GITHUB_REPO}" \ --branch-pattern="${BRANCH_PATTERN}" \ --build-config="cloudbuild.yaml" \ - --project="${PROJECT_ID}" \ - --quiet - echo "✓ Cloud Build trigger created: ${TRIGGER_NAME}" + --region="${REGION}" \ + --project="${PROJECT_ID}" --quiet + echo "✓ 2nd gen trigger created: ${TRIGGER_NAME}" else echo "✓ Trigger already exists: ${TRIGGER_NAME}" fi echo "" -echo "=== 06: CI/CD Setup COMPLETE ===" -echo " NOTE: GitHub connection must be pre-authorized at:" -echo " https://console.cloud.google.com/cloud-build/triggers/connect?project=${PROJECT_ID}" +echo "=== 06: CI/CD Setup COMPLETE (2nd gen) ===" +echo " Connection: ${CONNECTION_NAME}" +echo " Repo: ${GITHUB_OWNER}/${GITHUB_REPO}" +echo " Trigger: ${TRIGGER_NAME}" +echo "" +echo " PREREQUISITE: GitHub PAT must exist in Secret Manager:" +echo " gcloud secrets create github-token --data-file=<(echo -n \"ghp_TOKEN\")" +echo " OQ-04 resolved — no manual OAuth in Console required." echo " After first deploy, switch traffic manually:" echo " gcloud run services update-traffic ${CLOUD_RUN_SERVICE} --to-latest --region=${REGION}"