Skip to content

Add llvm-project-redist pipeline #100

Add llvm-project-redist pipeline

Add llvm-project-redist pipeline #100

Workflow file for this run

name: "Terraform: CI Pipelines Infrastructure"
on:
pull_request:
paths: ["buildkite/terraform/**"]
push:
branches: ["master"]
paths: ["buildkite/terraform/**"]
# go/github-security: Explicitly set minimum permissions
permissions:
contents: read # Required to check out the code
id-token: write # Required for Workload Identity Federation (WIF)
pull-requests: write # Required to post plan output as a comment
jobs:
# Job 1: Detect which organization folders changed
detect-changes:
runs-on: ubuntu-latest
outputs:
orgs: ${{ steps.process-orgs.outputs.orgs }}
steps:
- name: Checkout Code
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
with:
fetch-depth: 0
- name: Get Changed Files
id: changed-files
uses: tj-actions/changed-files@48d8f15b2aaa3d255ca5af3eba4870f807ce6b3c # v45
with:
files: buildkite/terraform/**
- name: Extract Orgs
id: process-orgs
shell: bash
run: |
CHANGED_FILES="${{ steps.changed-files.outputs.all_changed_files }}"
# Pull Specific Orgs -> Cut Org Name -> Sort Unique -> JSON Array
ORGS=$(echo "$CHANGED_FILES" | tr ' ' '\n' | \
grep -E -o "^buildkite/terraform/(bazel|bazel-trusted|bazel-testing)/" | cut -d/ -f3 | sort -u | \
jq -R -s -c 'split("\n") | map(select(length > 0))')
echo "DEBUG:ORGS changed are: $ORGS"
echo "DEBUG:Event Name is: ${{ github.event_name }}"
echo "DEBUG:Author is: ${{ github.event.pull_request.author_association }}"
echo "orgs=${ORGS:-[]}" >> "$GITHUB_OUTPUT"
# Job 2: Terraform Execution
terraform:
needs: detect-changes
# Run only if we have changed orgs AND (it's a push to master OR PR from trusted users)
if: needs.detect-changes.outputs.orgs != '[]'
runs-on: ubuntu-latest
# Lock per organization. Cancels old runs on PRs (saves time), but queues pushes (safe apply).
concurrency:
group: ${{ github.workflow }}-${{ matrix.org }}-${{ github.ref }}
cancel-in-progress: ${{ github.event_name == 'pull_request' }}
# Use environment for secret isolation and manual approvals
environment: ${{ matrix.org }}
strategy:
fail-fast: false # If one org fails, don't stop the others
matrix:
org: ${{ fromJSON(needs.detect-changes.outputs.orgs) }}
defaults:
run:
working-directory: ./buildkite/terraform/${{ matrix.org }}
steps:
- name: Checkout Code
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
#TODO: change this back to WIP once the provider request is approved
- name: Authenticate to Google Cloud
uses: google-github-actions/auth@7c6bc770dae815cd3e89ee6cdf493a5fab2cc093 # v3.0.0
with:
credentials_json: '${{ secrets.GCP_SA_KEY }}'
- name: Setup Terraform
uses: hashicorp/setup-terraform@b9cd54a3c349d3f38e8881555d616ced269862dd # v3.1.2
with:
terraform_wrapper: false
terraform_version: "1.9.5"
- name: Terraform Init
run: terraform init
- name: Terraform Plan
if: github.event_name == 'pull_request'
id: plan
env:
TF_VAR_buildkite_api_token: ${{ secrets.BUILDKITE_API_TOKEN }}
run: |
terraform plan -no-color -input=false -out=tfplan
terraform show -no-color tfplan > plan.txt
- name: Post Plan to PR
if: github.event_name == 'pull_request'
uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1
with:
script: |
const fs = require('fs');
let planOutput = "Plan file not found";
try {
planOutput = fs.readFileSync(`buildkite/terraform/${{ matrix.org }}/plan.txt`, 'utf8');
} catch (e) {
planOutput = "Error reading plan file: " + e.message;
}
// Regex to match "Plan: X to add, Y to change, Z to destroy."
const planRegex = /Plan:\s+(\d+)\s+to add,\s+(\d+)\s+to change,\s+(\d+)\s+to destroy\./;
const match = planOutput.match(planRegex);
let summary = `#### Terraform Plan for \`${{ matrix.org }}\` 📖`;
if (match) {
const [_, toAdd, toChange, toDestroy] = match;
summary += `\nPlan: ${toAdd} to add, ${toChange} to change, ${toDestroy} to destroy.`;
} else if (planOutput.includes("No changes.")) {
summary += `\nNo changes. Your infrastructure matches the configuration.`;
}
const maxLength = 64000;
let truncatedPlan = planOutput;
if (planOutput.length > maxLength) {
const msg = "\n... (truncated due to length. Read full plan in 'Terraform Plan' step of GitHub Actions run) ...";
truncatedPlan = planOutput.substring(0, maxLength) + msg;
}
const output = `${summary}\n<details><summary>Show Plan</summary>\n\n\`\`\`terraform\n${truncatedPlan}\n\`\`\`\n\n</details>`;
github.rest.issues.listComments({
issue_number: context.issue.number,
owner: context.repo.owner,
repo: context.repo.repo
}).then(({ data: comments }) => {
const botComment = comments.find(comment => comment.body.includes(`#### Terraform Plan for \`${{ matrix.org }}\``));
if (botComment) {
return github.rest.issues.updateComment({
comment_id: botComment.id,
owner: context.repo.owner,
repo: context.repo.repo,
body: output
});
} else {
return github.rest.issues.createComment({
issue_number: context.issue.number,
owner: context.repo.owner,
repo: context.repo.repo,
body: output
});
}
});
- name: Terraform Apply
if: github.ref == 'refs/heads/master' && github.event_name == 'push'
env:
TF_VAR_buildkite_api_token: ${{ secrets.BUILDKITE_API_TOKEN }}
run: terraform apply -auto-approve -input=false