generated from danielcgilibert/blog-template
-
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
68fef60
commit 93d0319
Showing
1 changed file
with
224 additions
and
0 deletions.
There are no files selected for viewing
224 changes: 224 additions & 0 deletions
224
src/content/blog/streamlit-deployment-guide-part-4-github-tf-workflow.mdx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,224 @@ | ||
--- | ||
heroImage: /src/assets/images/Terraform.png | ||
category: CICD | ||
description: >- | ||
A step-by-step guide to configure a GitHub Workflow that executes Terraform commands to provision Infrastructure on Azure. | ||
pubDate: 2024-07-16 | ||
draft: true | ||
tags: | ||
- terraform | ||
- azure | ||
- iac | ||
- github | ||
title: >- | ||
Streamlit Deployment Guide Part 4: GitHub Workflow for Terraform Apply & Destroy | ||
--- | ||
|
||
This showcases a GitHub Workflow walkthrough of executing the necessary Terraform commands to provision and tear down the Azure resources for the Streamlit application. It continues a series detailing the process of deploying a Streamlit app to Azure, broken down into the following parts: | ||
|
||
- [**Part 1**: Containerizing a Streamlit app.](https://blog.waynegoosen.com/post/streamlit-deployment-guide-part-1-containerization/) | ||
- [**Part 2**: GitHub Workflow for Building and Publishing to ghcr.io](https://blog.waynegoosen.com/post/streamlit-deployment-guide-part-2-github-workflow/) | ||
- [**Part 3**: Azure Infrastructure via Terraform](https://blog.waynegoosen.com/post/streamlit-deployment-guide-part-3-azure-infra/) | ||
- **Part 4**: GitHub Workflow for Terraform Apply & Destroy **You are here** 😊 | ||
|
||
Do you want to deploy your Streamlit application on Azure right now? Use the [template repository](https://github.com/WayneGoosen/azure-streamlit-poc) 🚀 | ||
|
||
## TL;DR | ||
|
||
See the [completed GitHub Workflow](#completed-workflow). | ||
|
||
## Prerequisites | ||
|
||
A basic understanding of GitHub Actions is required and the Workflow assumes you have the files from Part 3: | ||
|
||
- /infra/main.tf | ||
- /infra/providers.tf | ||
- /infra/variables.tf | ||
- /infra/locals.tf | ||
- /infra/web-app.tf | ||
|
||
If you have your own Terraform configuration, ensure all the dependent files are available and are stored within /infra folder for this Workflows to function correctly. | ||
|
||
## Create a GitHub Workflow | ||
|
||
The Workflow file should be stored within the following folder: `.github/workflows/`. A concise name could be `docker-image-build-and-push.yaml`. | ||
|
||
### Completed Apply Workflow | ||
|
||
```yaml | ||
name: Terraform Plan & Apply Infrastructure | ||
|
||
on: | ||
push: | ||
branches: ['main'] | ||
paths: | ||
- 'infra/**' | ||
tags: | ||
- '*' | ||
workflow_dispatch: | ||
|
||
env: | ||
TF_VAR_resource_group_name: 'rg-streamlit-poc' | ||
WORKING_DIRECTORY: './infra' | ||
|
||
jobs: | ||
terraform: | ||
runs-on: ubuntu-latest | ||
environment: production | ||
permissions: | ||
id-token: write | ||
steps: | ||
- name: Checkout code | ||
uses: actions/checkout@v4 | ||
with: | ||
fetch-depth: 0 | ||
|
||
# image name needs to be lowercase, some accounts have uppercase letters | ||
- name: Get owner/repo name and convert to lowercase | ||
id: get-image-name | ||
run: echo "image-name=$(echo ${{ github.repository }} | tr '[:upper:]' '[:lower:]')" >> $GITHUB_OUTPUT | ||
|
||
- name: Extract image tag | ||
id: extract-tag | ||
run: | | ||
if [[ $GITHUB_REF == refs/tags/* ]]; then | ||
TAG=${GITHUB_REF#refs/tags/} | ||
else | ||
TAG=$(git describe --tags --abbrev=0) | ||
fi | ||
echo "tag=$TAG" >> $GITHUB_OUTPUT | ||
- name: Azure login | ||
uses: azure/login@v2 | ||
with: | ||
client-id: ${{ secrets.AZURE_ENTRA_ID_CLIENT_ID }} | ||
tenant-id: ${{ secrets.AZURE_ENTRA_ID_TENANT_ID }} | ||
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }} | ||
|
||
- name: Setup Terraform | ||
uses: hashicorp/setup-terraform@v3 | ||
with: | ||
terraform_version: 1.8.4 | ||
|
||
- name: Terraform fmt | ||
id: fmt | ||
run: terraform fmt -check | ||
continue-on-error: true | ||
|
||
- name: Terraform Init | ||
id: init | ||
working-directory: ${{ env.WORKING_DIRECTORY }} | ||
env: | ||
ARM_CLIENT_ID: ${{ secrets.AZURE_ENTRA_ID_CLIENT_ID }} | ||
ARM_TENANT_ID: ${{ secrets.AZURE_ENTRA_ID_TENANT_ID }} | ||
ARM_SUBSCRIPTION_ID: ${{ secrets.AZURE_SUBSCRIPTION_ID }} | ||
ARM_USE_OIDC: true | ||
run: terraform init | ||
|
||
- name: Terraform Validate | ||
id: validate | ||
working-directory: ${{ env.WORKING_DIRECTORY }} | ||
run: terraform validate -no-color | ||
|
||
- name: Terraform Plan | ||
id: plan | ||
env: | ||
ARM_CLIENT_ID: ${{ secrets.AZURE_ENTRA_ID_CLIENT_ID }} | ||
ARM_TENANT_ID: ${{ secrets.AZURE_ENTRA_ID_TENANT_ID }} | ||
ARM_SUBSCRIPTION_ID: ${{ secrets.AZURE_SUBSCRIPTION_ID }} | ||
ARM_USE_OIDC: true | ||
TF_VAR_docker_image_name: '${{ steps.get-image-name.outputs.image-name }}:${{ steps.extract-tag.outputs.tag }}' | ||
working-directory: ${{ env.WORKING_DIRECTORY }} | ||
run: terraform plan -no-color | ||
continue-on-error: false | ||
|
||
- name: Terraform Apply (auto-approve) | ||
working-directory: ${{ env.WORKING_DIRECTORY }} | ||
env: | ||
ARM_CLIENT_ID: ${{ secrets.AZURE_ENTRA_ID_CLIENT_ID }} | ||
ARM_TENANT_ID: ${{ secrets.AZURE_ENTRA_ID_TENANT_ID }} | ||
ARM_SUBSCRIPTION_ID: ${{ secrets.AZURE_SUBSCRIPTION_ID }} | ||
ARM_USE_OIDC: true | ||
TF_VAR_docker_image_name: '${{ steps.get-image-name.outputs.image-name }}:${{ steps.extract-tag.outputs.tag }}' | ||
run: terraform apply -auto-approve | ||
``` | ||
#### Workflow Walkthrough | ||
##### Workflow Definition | ||
```yaml | ||
name: Docker Image Build and Push | ||
``` | ||
The name of the workflow which is shown under the Actions tab. This allows you to set a readable name for your Workflow, if omitted the file name will be shown. | ||
##### Triggers | ||
```yaml | ||
on: | ||
push: | ||
branches: ['main'] | ||
paths: | ||
- 'app/**' | ||
workflow_dispatch: | ||
``` | ||
The workflow triggers on pushes to the "main" branch and only if the changes are made in the 'app' directory. The 'workflow_dispatch' allows the workflow to be triggered manually. | ||
### Completed Destroy Workflow | ||
```yaml | ||
name: Terraform Destroy Inrastructure | ||
|
||
on: workflow_dispatch | ||
|
||
env: | ||
TF_VAR_docker_image_name: 'waynegoosen/azure-streamlit-poc:0.1.2' | ||
TF_VAR_resource_group_name: 'rg-streamlit-poc' | ||
WORKING_DIRECTORY: './infra' | ||
|
||
jobs: | ||
terraform: | ||
runs-on: ubuntu-latest | ||
environment: production | ||
permissions: | ||
id-token: write | ||
steps: | ||
- name: Checkout code | ||
uses: actions/checkout@v4 | ||
with: | ||
fetch-depth: 0 | ||
|
||
- name: Azure login | ||
uses: azure/login@v2 | ||
with: | ||
client-id: ${{ secrets.AZURE_AD_CLIENT_ID }} | ||
tenant-id: ${{ secrets.AZURE_AD_TENANT_ID }} | ||
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }} | ||
|
||
- name: Setup Terraform | ||
uses: hashicorp/setup-terraform@v3 | ||
with: | ||
terraform_version: 1.8.0 | ||
|
||
- name: Terraform Init | ||
id: init | ||
working-directory: ${{ env.WORKING_DIRECTORY }} | ||
env: | ||
ARM_CLIENT_ID: ${{ secrets.AZURE_AD_CLIENT_ID }} | ||
ARM_SUBSCRIPTION_ID: ${{ secrets.AZURE_SUBSCRIPTION_ID }} | ||
ARM_TENANT_ID: ${{ secrets.AZURE_AD_TENANT_ID }} | ||
ARM_USE_OIDC: true | ||
run: terraform init | ||
|
||
- name: Terraform Destroy (auto-approve) | ||
id: destroy | ||
working-directory: ${{ env.WORKING_DIRECTORY }} | ||
env: | ||
ARM_CLIENT_ID: ${{ secrets.AZURE_AD_CLIENT_ID }} | ||
ARM_SUBSCRIPTION_ID: ${{ secrets.AZURE_SUBSCRIPTION_ID }} | ||
ARM_TENANT_ID: ${{ secrets.AZURE_AD_TENANT_ID }} | ||
ARM_USE_OIDC: true | ||
run: terraform destroy -auto-approve | ||
``` |