There are several options for deploying resources in Azure with Bicep from a GitHub repository. You can use Azure CLI or Azure PowerShell, but you can also use the GitHub Action Bicep-deploy.
The Bicep-Deploy (Azure/bicep-deploy@v2) action is versatile and can be used in different situations. You can deploy or test a Bicep template or create a stack using a deployment stack.
Every bicep-deploy action must have a name and a location. The name is a free text, the location must be a valid Azure Region. A description can be added to the action with the parameter description, but it is optional.
The bicep-deploy action can deploy Bicep templates and Azure Stack. The “type” parameter determines this: deployment for Bicep template deployment or deploymentStack for Stack deployment.
The second parameter to use with the bicep-deploy is “operation”. This parameter can take two sets of values, depending on the type of deployment.
For Bicep deployment
- Create, to create the infrastructure using the bicep code
- Validate, to lint the Bicep code
- WhatIf, to perform a WhatIf (that can be used with the validation-level and what-if-exclude-change-types parameters)
For DeploymentStack
- Create, to create the deploymentStack
- Validate, to lint the code
- Delete, to delete the deploymentStack
The scope also depends on the deployment type; tenant, managementGroup, subscription, resourceGroup for deployment and managementGroup, subscription, resourceGroup for deploymentStack.
Some parameters are specific to deploymentStack
- action-on-unmanage-resources Detach or delete
- action-on-unmanage-resourcegroups Detach or delete
- action-on-unmanage-managementgroup Detach or delete
- deny-settings-mode denyDelete, denyWriteAndDelete, or none
- deny-settings-excluded-actions List of role-based management operations that will not be deny
- deny-settings-excluded-principals List of Service Principal that will not be deny
- deny-settings-apply-to-child-scopes True if you want to apply the deny to child resources
- bypass-stack-out-of-sync-error To run the deployment when the stack is not correctly in sync
Let’s try to view that with a Bicep Deployment.
We have a simple Bicep Code to deploy a VNET with two subnets.
param location string = resourceGroup().location
@description('VNet name')
param vnetName string = 'vnet1'
@description('Vnet Address space')
param vnetAddressPrefix string = '10.0.0.0/8'
@description('Subnet1 Prefix')
param subnet1Prefix string = '10.0.0.0/24'
@description('Subnet1 Name')
param subnet1Name string = 'sub1'
@description('Subnet2 Prefix')
param subnet2Prefix string = '10.0.1.0/24'
@description('Subnet2 Name')
param subnet2Name string = 'sub2'
// an unused variable to test Bicep linter
var unusedVariable = 'nice to have'
resource vnet 'Microsoft.Network/virtualNetworks@2024-01-01' = {
name: vnetName
location: location
properties: {
addressSpace: {
addressPrefixes: [
vnetAddressPrefix
]
}
}
}
resource subnet1 'Microsoft.Network/virtualNetworks/subnets@2024-01-01' = {
parent: vnet
name: subnet1Name
properties: {
addressPrefix: subnet1Prefix
}
}
resource subnet2 'Microsoft.Network/virtualNetworks/subnets@2024-01-01' = {
parent: vnet
name: subnet2Name
properties: {
addressPrefix: subnet2Prefix
}
}
We need to set the workflow.
I already covered how to test, apply a what-if, and deploy a Bicep template with PowerShell in a previous [blog post]((https://dev.to/omiossec/create-a-github-pipeline-to-test-review-and-deploy-a-bicep-template-h45), here I will reproduce the same template I used before and deploy a Stack.
First, we need an identity to connect to Azure, I will use a Federated identity; the process is described in my last post. You can check this page
The identity will be used to connect to Azure using 3 secrets: AZURE_CLIENT_ID, secrets.AZURE_TENANT_ID, and secrets.AZURE_SUBSCRIPTION_ID in a GitHub environment called DevTo-Demo.
name: Bicep-deploy demo
on:
push:
branches:
- main
permissions:
id-token: write
contents: read
jobs:
Bicep-deploy-demo:
name: Bicep-Deploy Demo
runs-on: ubuntu-latest
environment: DevTo-Demo
steps:
- name: Checkout
uses: actions/checkout@v4
- name: login to Azure
uses: azure/login@v2
with:
client-id: ${{ secrets.AZURE_CLIENT_ID }}
tenant-id: ${{ secrets.AZURE_TENANT_ID }}
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
enable-AzPSSession: true
The first action should be to test the code with Bicep Lint with the validate operation.
- name: Validate Bicep Code
uses: azure/bicep-deploy@v2
with:
type: deployment
operation: validate
name: Validate-code
scope: resourceGroup
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
resource-group-name: bicep-deploy
template-file: ./Bicep/main.bicep
This will check for errors in the Bicep code by using the default rules
You can use a bicepconfig.json rule to customize the linter see
For example, there is an unused variable in the Bicep code
// an unused variable to test linter
var unusedVariable = 'nice to have'
By default, it will trigger a warning, but this behavior can be changed by using the bicepconfig.json
"no-unused-vars": {
"level": "error"
},
The second action is to perform a what-if to see what will be deployed/changed with the Bicep code.
- name: Execute Whatif
uses: azure/bicep-deploy@v2
with:
type: deployment
operation: whatIf
name: whatIf-Bicep_code
scope: resourceGroup
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
resource-group-name: bicep-deploy
template-file: ./Bicep/main.bicep
The result of the what-if action will be something like that (if it is the first time you run it).
Scope: /subscriptions/***/resourceGroups/bicep-deploy
34
35 + Microsoft.Network/virtualNetworks/vnet1 [2024-01-01]
36
37 apiVersion: "2024-01-01"
38 id: "/subscriptions/***/resourceGroups/bicep-deploy/providers/Microsoft.Network/virtualNetworks/vnet1"
39 location: "westeurope"
40 name: "vnet1"
41 properties.addressSpace.addressPrefixes: [
42 0: "10.0.0.0/8"
43 ] properties.subnets: [
44 0:
45
46 name: "sub1"
47 properties.addressPrefix: "10.0.0.0/24"
48
49 1:
50
51 name: "sub2"
52 properties.addressPrefix: "10.0.1.0/24"
53
54 ] type: "Microsoft.Network/virtualNetworks"
55
56 + Microsoft.Network/virtualNetworks/vnet1/subnets/sub1 [2024-01-01]
57
58 apiVersion: "2024-01-01"
59 id: "/subscriptions/***/resourceGroups/bicep-deploy/providers/Microsoft.Network/virtualNetworks/vnet1/subnets/sub1"
60 name: "sub1"
61 properties.addressPrefix: "10.0.0.0/24"
62 type: "Microsoft.Network/virtualNetworks/subnets"
63
64 + Microsoft.Network/virtualNetworks/vnet1/subnets/sub2 [2024-01-01]
65
66 apiVersion: "2024-01-01"
67 id: "/subscriptions/***/resourceGroups/bicep-deploy/providers/Microsoft.Network/virtualNetworks/vnet1/subnets/sub2"
68 name: "sub2"
69 properties.addressPrefix: "10.0.1.0/24"
70 type: "Microsoft.Network/virtualNetworks/subnets"
71
72Resource changes: 3 to create.
The next step will be to deploy the resource from the template. But before deploying the Bicep template, you would like to have a validation of the Bicep What-if action, to check if nothing wrong will happen.
You need to set up a new GitHub environment where the option “Required reviewers” is selected.
Then you add a new job to deploy the Bicep template and add the “need” to reference the previous job.
Bicep-deploy-after-review:
name: run azure deploy
runs-on: ubuntu-latest
environment: bicep-deploy
needs: Bicep-deploy-demo
steps:
- name: Checkout
uses: actions/checkout@v4
- name: login to Azure
uses: azure/login@v2
with:
client-id: ${{ secrets.AZURE_CLIENT_ID }}
tenant-id: ${{ secrets.AZURE_TENANT_ID }}
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
enable-AzPSSession: true
- name: Deploy Bicep Code
uses: azure/bicep-deploy@v2
with:
type: deployment
operation: create
name: deploy-Bicep_code
scope: resourceGroup
subscription-id: ${{ secrets.AZURE_SUBSCRIPTION_ID }}
resource-group-name: bicep-deploy
template-file: ./Bicep/main.bicep
In part 2, I will cover deploymentStack
Top comments (0)