-
Notifications
You must be signed in to change notification settings - Fork 0
DevOps Pipelines
Weixian edited this page May 25, 2026
·
7 revisions
Proposed 3 GitHub Action workflows to support continuous delivery with our branching strategy.
name: Main branch to SIT
on:
push:
branches:
- main
permissions:
contents: read
id-token: write # required for Azure OIDC login
env:
APP_NAME: my-app
ACR_NAME: myacr # e.g. myacr (without .azurecr.io)
ACR_LOGIN_SERVER: myacr.azurecr.io
RESOURCE_GROUP: rg-sit
CONTAINER_APP_NAME: my-app-sit
CONTAINER_APP_ENV: cae-sit # Container Apps environment name
concurrency:
group: main-sit-deploy
cancel-in-progress: true
jobs:
# -------------------------
# 1. BUILD & PUSH IMAGE
# -------------------------
build:
name: Build, Test & Push Image
runs-on: ubuntu-latest
outputs:
image_tag: ${{ steps.vars.outputs.image_tag }}
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Install dependencies
run: echo "install dependencies"
- name: Run unit tests
run: echo "run tests"
- name: Set image tag
id: vars
run: echo "image_tag=${GITHUB_SHA::7}" >> $GITHUB_OUTPUT
- name: Azure Login (OIDC)
uses: azure/login@v2
with:
client-id: ${{ secrets.AZURE_CLIENT_ID }}
tenant-id: ${{ secrets.AZURE_TENANT_ID }}
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
- name: Log in to ACR
run: az acr login --name ${{ env.ACR_NAME }}
- name: Build and push Docker image
run: |
docker build -t ${{ env.ACR_LOGIN_SERVER }}/${{ env.APP_NAME }}:${{ steps.vars.outputs.image_tag }} .
docker push ${{ env.ACR_LOGIN_SERVER }}/${{ env.APP_NAME }}:${{ steps.vars.outputs.image_tag }}
# -------------------------
# 2. DEPLOY TO SIT (AUTO)
# -------------------------
deploy-sit:
name: Deploy to SIT
needs: build
runs-on: ubuntu-latest
environment: sit # no approval
steps:
- name: Azure Login (OIDC)
uses: azure/login@v2
with:
client-id: ${{ secrets.AZURE_CLIENT_ID }}
tenant-id: ${{ secrets.AZURE_TENANT_ID }}
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
- name: Deploy to Azure Container Apps
uses: azure/container-apps-deploy-action@v2
with:
resourceGroup: ${{ env.RESOURCE_GROUP }}
containerAppName: ${{ env.CONTAINER_APP_NAME }}
containerAppEnvironment: ${{ env.CONTAINER_APP_ENV }}
imageToDeploy: ${{ env.ACR_LOGIN_SERVER }}/${{ env.APP_NAME }}:${{ needs.build.outputs.image_tag }}
targetPort: 8080
ingress: external
- name: Smoke Test
run: |
echo "Running smoke tests on SIT..."
FQDN=$(az containerapp show -n ${{ env.CONTAINER_APP_NAME }} -g ${{ env.RESOURCE_GROUP }} --query properties.configuration.ingress.fqdn -o tsv)
curl -fsSL "https://${FQDN}/health" || exit 1name: Release branch → UAT → pre-prod → production
on:
push:
branches:
- 'release/*'
permissions:
contents: write # needed for tagging
id-token: write # needed for Azure OIDC login
env:
APP_NAME: my-app
ACR_NAME: myacr # without .azurecr.io
ACR_LOGIN_SERVER: myacr.azurecr.io
TARGET_PORT: 8080
jobs:
# -------------------------
# 1. BUILD ONCE & PUSH IMAGE
# -------------------------
build:
name: Build & Push Image
runs-on: ubuntu-latest
# Skip if the commit is a merge of a hotfix (avoid re-deploying hotfix merges to UAT)
if: ${{ !(contains(toLowerCase(github.event.head_commit.message), 'merge') && contains(toLowerCase(github.event.head_commit.message), 'hotfix')) }}
outputs:
version: ${{ steps.extract_version.outputs.version }}
image: ${{ steps.image.outputs.image }}
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Extract version from branch
id: extract_version
run: |
BRANCH_NAME=${GITHUB_REF#refs/heads/}
VERSION=${BRANCH_NAME#release/}
echo "version=$VERSION" >> $GITHUB_OUTPUT
- name: Compute image reference
id: image
run: |
SHORT_SHA=${GITHUB_SHA::7}
IMAGE="${{ env.ACR_LOGIN_SERVER }}/${{ env.APP_NAME }}:${{ steps.extract_version.outputs.version }}-${SHORT_SHA}"
echo "image=$IMAGE" >> $GITHUB_OUTPUT
- name: Azure Login (OIDC)
uses: azure/login@v2
with:
client-id: ${{ secrets.AZURE_CLIENT_ID }}
tenant-id: ${{ secrets.AZURE_TENANT_ID }}
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
- name: Log in to ACR
run: az acr login --name ${{ env.ACR_NAME }}
- name: Build and push Docker image
run: |
docker build -t ${{ steps.image.outputs.image }} .
docker push ${{ steps.image.outputs.image }}
# -------------------------
# 2. DEPLOY TO UAT (AUTO)
# -------------------------
deploy-uat:
name: Deploy to UAT
needs: build
runs-on: ubuntu-latest
environment: uat # no approval
env:
RESOURCE_GROUP: rg-uat
CONTAINER_APP_NAME: my-app-uat
CONTAINER_APP_ENV: cae-uat
steps:
- name: Azure Login (OIDC)
uses: azure/login@v2
with:
client-id: ${{ secrets.AZURE_CLIENT_ID }}
tenant-id: ${{ secrets.AZURE_TENANT_ID }}
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
- name: Deploy to Azure Container Apps (UAT)
uses: azure/container-apps-deploy-action@v2
with:
resourceGroup: ${{ env.RESOURCE_GROUP }}
containerAppName: ${{ env.CONTAINER_APP_NAME }}
containerAppEnvironment: ${{ env.CONTAINER_APP_ENV }}
imageToDeploy: ${{ needs.build.outputs.image }}
targetPort: ${{ env.TARGET_PORT }}
ingress: external
- name: Smoke Test (UAT)name: Hotfix branch → Pre-production → Prod
on:
push:
branches:
- 'hotfix/*' # ONLY triggers on hotfix branches
permissions:
contents: write # needed for tagging
id-token: write # needed for Azure OIDC login
env:
APP_NAME: my-app
ACR_NAME: myacr # without .azurecr.io
ACR_LOGIN_SERVER: myacr.azurecr.io
TARGET_PORT: 8080
jobs:
# -------------------------
# 1. BUILD ONCE & PUSH IMAGE
# -------------------------
build-and-test-hotfix:
name: Build & Verify Hotfix
runs-on: ubuntu-latest
outputs:
version: ${{ steps.extract_version.outputs.version }}
image: ${{ steps.image.outputs.image }}
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Extract hotfix version from branch
id: extract_version
run: |
BRANCH_NAME=${GITHUB_REF#refs/heads/}
VERSION=${BRANCH_NAME#hotfix/}
echo "version=$VERSION" >> $GITHUB_OUTPUT
- name: Run hotfix tests
run: echo "Running unit tests for hotfix..."
- name: Compute image reference
id: image
run: |
SHORT_SHA=${GITHUB_SHA::7}
IMAGE="${{ env.ACR_LOGIN_SERVER }}/${{ env.APP_NAME }}:hotfix-${{ steps.extract_version.outputs.version }}-${SHORT_SHA}"
echo "image=$IMAGE" >> $GITHUB_OUTPUT
- name: Azure Login (OIDC)
uses: azure/login@v2
with:
client-id: ${{ secrets.AZURE_CLIENT_ID }}
tenant-id: ${{ secrets.AZURE_TENANT_ID }}
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
- name: Log in to ACR
run: az acr login --name ${{ env.ACR_NAME }}
- name: Build and push Docker image
run: |
docker build -t ${{ steps.image.outputs.image }} .
docker push ${{ steps.image.outputs.image }}
# -------------------------
# 2. DEPLOY TO PRE-PROD (MANUAL APPROVAL)
# -------------------------
deploy-preprod:
name: Deploy to Pre-Prod
needs: build-and-test-hotfix
runs-on: ubuntu-latest
environment: preprod # approval in GitHub UI
env:
RESOURCE_GROUP: rg-preprod
CONTAINER_APP_NAME: my-app-preprod
CONTAINER_APP_ENV: cae-preprod
steps:
-
Agile Delivery
- Product Requirement Template
- Documenting Product Requirements
- Estimation & Sizing
- DevOps
-
Software Architecture Design
- Agent Engineering
- Logging
- Tech Stack
- Testing & Quality
- Observability & Operations