Skip to content

Run deploy

Run deploy #77

Workflow file for this run

# This workflow build and push a Docker container to Google Artifact Registry and deploy it on Cloud Run when a commit is pushed to the $default-branch branch
#
# Overview:
#
# 1. Authenticate to Google Cloud
# 2. Authenticate Docker to Artifact Registry
# 3. Build a docker container
# 4. Publish it to Google Artifact Registry
# 5. Deploy it to Cloud Run
#
# The workflow uses GH Secrets managed by Terraform:
# - GCP_PROJECT_ID
# - GCP_REGION
# - <environment>_GCP_SA_KEY - credentials json for authentication
# - <environment>_CLIENT_ENV_TF_MANAGED
# - <environment>_CMS_ENV_TF_MANAGED
# - <environment>_CLIENT_REPOSITORY
# - <environment>_CLIENT_SERVICE
# - <environment>_CMS_REPOSITORY
# - <environment>_CMS_SERVICE
#
# it also uses the following secrets not managed by Terraform:
# - <environment>_CLIENT_ENV
name: Run deploy
on:
workflow_dispatch:
push:
branches:
- main
- develop
- infrastructure/setup
paths:
- 'frontend/**'
- 'cms/**'
- '.github/workflows/*'
env:
PROJECT_ID: ${{ secrets.GCP_PROJECT_ID }}
GAR_LOCATION: ${{ secrets.GCP_REGION }}
REGION: ${{ secrets.GCP_REGION }}
jobs:
deploy_client:
# Add 'id-token' with the intended permissions for workload identity federation
permissions:
contents: 'read'
id-token: 'write'
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Extract branch name
shell: bash
run: echo "branch=${GITHUB_HEAD_REF:-${GITHUB_REF#refs/heads/}}" >> $GITHUB_OUTPUT
id: extract_branch
- name: Extract environment name
env:
ENVIRONMENT: ${{ steps.extract_branch.outputs.branch == 'main' && 'PRODUCTION' || 'STAGING' }}
run: echo "environment=$ENVIRONMENT" >> $GITHUB_OUTPUT
id: extract_environment
#- name: Google Auth authentication via credentials json
- name: Google Auth
id: auth
uses: 'google-github-actions/auth@v1'
with:
credentials_json: "${{ secrets[format('{0}_GCP_SA_KEY', steps.extract_environment.outputs.environment)] }}"
token_format: 'access_token'
# Authenticate Docker to Google Cloud Artifact Registry via credentials json
- name: Docker Auth
id: docker-auth
uses: 'docker/login-action@v3'
with:
registry: ${{ env.GAR_LOCATION }}-docker.pkg.dev
username: _json_key
password: ${{ secrets[format('{0}_GCP_SA_KEY', steps.extract_environment.outputs.environment)] }}
- name: Copy env variables to docker
run: |
echo "${{ secrets[format('{0}_CLIENT_ENV', steps.extract_environment.outputs.environment)] }}" > frontend/.env.local
# append Terraform managed secrets
echo "${{ secrets[format('{0}_CLIENT_ENV_TF_MANAGED', steps.extract_environment.outputs.environment)] }}" >> frontend/.env.local
- name: Build and Push Container
env:
REPOSITORY: ${{ secrets[format('{0}_CLIENT_REPOSITORY', steps.extract_environment.outputs.environment)] }}
SERVICE: ${{ secrets[format('{0}_CLIENT_SERVICE', steps.extract_environment.outputs.environment)] }}
run: |-
docker build -f frontend/Dockerfile.prod -t "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:${{ github.sha }}" ./frontend
docker push "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:${{ github.sha }}"
# tag as "latest"
docker tag "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:${{ github.sha }}" "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:latest"
docker push "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:latest"
- name: Deploy to Cloud Run
env:
REPOSITORY: ${{ secrets[format('{0}_CLIENT_REPOSITORY', steps.extract_environment.outputs.environment)] }}
SERVICE: ${{ secrets[format('{0}_CLIENT_SERVICE', steps.extract_environment.outputs.environment)] }}
id: deploy
uses: google-github-actions/deploy-cloudrun@v1
with:
service: ${{ env.SERVICE }}
region: ${{ env.REGION }}
image: ${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:${{ github.sha }}
# NOTE: You can also set env variables here:
# env_vars: |
# NODE_ENV=production
# TOKEN_EXPIRE=6400
# If required, use the Cloud Run url output in later steps
- name: Show Output
run: echo ${{ steps.deploy.outputs.url }}
deploy_cms:
# Add 'id-token' with the intended permissions for workload identity federation
permissions:
contents: 'read'
id-token: 'write'
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Extract branch name
shell: bash
run: echo "branch=${GITHUB_HEAD_REF:-${GITHUB_REF#refs/heads/}}" >> $GITHUB_OUTPUT
id: extract_branch
- name: Extract environment name
env:
ENVIRONMENT: ${{ steps.extract_branch.outputs.branch == 'main' && 'PRODUCTION' || 'STAGING' }}
run: echo "environment=$ENVIRONMENT" >> $GITHUB_OUTPUT
id: extract_environment
#- name: Google Auth authentication via credentials json
- name: Google Auth
id: auth
uses: 'google-github-actions/auth@v1'
with:
credentials_json: "${{ secrets[format('{0}_GCP_SA_KEY', steps.extract_environment.outputs.environment)] }}"
token_format: 'access_token'
# Authenticate Docker to Google Cloud Artifact Registry via credentials json
- name: Docker Auth
id: docker-auth
uses: 'docker/login-action@v3'
with:
registry: ${{ env.GAR_LOCATION }}-docker.pkg.dev
username: _json_key
password: ${{ secrets[format('{0}_GCP_SA_KEY', steps.extract_environment.outputs.environment)] }}
- name: Copy env variables to docker
run: |
echo "${{ secrets[format('{0}_CMS_ENV_TF_MANAGED', steps.extract_environment.outputs.environment)] }}" > cms/.env
- name: Build and Push Container
env:
REPOSITORY: ${{ secrets[format('{0}_CMS_REPOSITORY', steps.extract_environment.outputs.environment)] }}
SERVICE: ${{ secrets[format('{0}_CMS_SERVICE', steps.extract_environment.outputs.environment)] }}
run: |-
docker build -f cms/Dockerfile.prod -t "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:${{ github.sha }}" ./cms
docker push "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:${{ github.sha }}"
# tag as "latest"
docker tag "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:${{ github.sha }}" "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:latest"
docker push "${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:latest"
- name: Deploy to Cloud Run
env:
REPOSITORY: ${{ secrets[format('{0}_CMS_REPOSITORY', steps.extract_environment.outputs.environment)] }}
SERVICE: ${{ secrets[format('{0}_CMS_SERVICE', steps.extract_environment.outputs.environment)] }}
id: deploy
uses: google-github-actions/deploy-cloudrun@v1
with:
service: ${{ env.SERVICE }}
region: ${{ env.REGION }}
image: ${{ env.GAR_LOCATION }}-docker.pkg.dev/${{ env.PROJECT_ID }}/${{ env.REPOSITORY }}/${{ env.SERVICE }}:${{ github.sha }}
# NOTE: You can also set env variables here:
# env_vars: |
# NODE_ENV=production
# TOKEN_EXPIRE=6400
# If required, use the Cloud Run url output in later steps
- name: Show Output
run: echo ${{ steps.deploy.outputs.url }}