Week 14 - Infrastructure as Code

Why use Infrastructure as Code

IaC concepts

Azure Bicep

Bicep in practice

Deploy Bicep from CI/CD

Practice

Assignment

Gotchas & Pitfalls

Glossary: Week 14

Career relevance: Week 14

History of IaC

Slides (PDF)

Deleting infrastructure

This page is optional. Nothing here is required for Week 14's learning goals or the assignment. Back to the Going Further overview.

Week 14 teaches one deletion path: you created a storage account, so you delete it with az resource delete. That is deliberate, and it is the right habit on a shared class subscription. This page explains the two mechanisms real teams use instead, and why the obvious-sounding one is on its way out.

Why removing a line does nothing

Deleting a resource from your .bicep file does not delete it from Azure. That surprise is the week's first gotcha, and it comes from the deployment mode.

Incremental mode (the default)

In incremental mode, Azure Resource Manager creates and updates everything in your template, and leaves alone anything in the resource group that your template does not mention. This is the default, and Microsoft recommends it.

One thing here catches people out, and it is not the deletion behaviour. Within a resource that is in your template, properties are not merged. Redeploying reapplies every property:

<aside> ❗ A common misunderstanding is that properties you leave out stay unchanged. They do not. Resource Manager treats a missing property as "set this back to its default". Your resource block is the final state of the resource, not a patch on top of it.

</aside>

That is why your Bicep file must carry every non-default value you care about, not only the ones you are currently changing.

Complete mode, and why not to reach for it

In complete mode, Resource Manager deletes resources that live in the resource group but are absent from your template. On paper that is exactly what a newcomer expects. In practice, Microsoft now labels it not recommended and says it "will be gradually deprecated" in favour of deployment stacks.

Set it, if you ever meet it in an old pipeline, with --mode Complete:

# Shown so you recognise it in someone else's script. Do not run this on $CLASS_RG.
az deployment group create \
  --mode Complete \
  --resource-group ExampleResourceGroup \
  --template-file main.bicep

The reasons to avoid it are worth knowing, because they are the same reasons the class subscription would suffer:

<aside> ⚠️ If you ever do meet complete mode, run what-if first. It is the only thing that shows you the deletions before they happen. On a shared resource group, a complete-mode deploy of your own template would try to remove every classmate's account.

</aside>

Example

Resource group holds A, B, C. Your template declares A, B, D.

Mode Result
Incremental (default) A, B, C, D. C is untouched, D is added.
Complete A, B, D. C is deleted.

Deployment stacks: the current answer

A deployment stack is an Azure resource (Microsoft.Resources/deploymentStacks) that manages a group of resources as one unit. It records which resources it created, so when you remove a resource from the template, the stack knows that resource is now unmanaged and can delete it for you. It is the supported way to get "the file is the whole truth" behaviour.

az stack group create \
  --name my-stack \
  --resource-group "$CLASS_RG" \
  --template-file main.bicep \
  --action-on-unmanage detachAll \
  --deny-settings-mode none

Two flags carry the meaning:

--action-on-unmanage

What happens to a resource once the stack stops managing it, either because you removed it from the template or because you deleted the stack:

Value Effect
detachAll Leave the resources and resource groups in Azure. The stack just forgets them.
deleteResources Delete the resources, keep the resource groups.
deleteAll Delete the resources and the resource groups.

detachAll is the safe default to start with, and it is what the quickstart uses. deleteAll is the one that makes deletion feel like Terraform, and the one that removes a resource group with everything in it.

--deny-settings-mode

Stacks can also lock what they manage, so nobody removes a resource by hand in the portal. none, denyDelete, or denyWriteAndDelete. This is how a platform team stops drift at the source rather than detecting it later with what-if.

Note the boundary: deny settings apply to control plane operations only. A storage account and a blob container are control plane, so a stack manages them; the blobs inside the container are data plane and are not covered.

Deployment stacks need Azure CLI 2.61.0 or later.

Why you cannot try stacks this week

Not a curriculum choice: a permissions one. The class role HYF Data Track Student IaC grants Microsoft.Resources/deployments/*, and deployment stacks are a different resource type, Microsoft.Resources/deploymentStacks/*. Run az stack group create with your student credentials and Azure answers AuthorizationFailed.

That is deliberate. A stack with --action-on-unmanage deleteAll pointed at a shared resource group is one typo away from deleting ten people's work, which is exactly the blast radius the class role exists to prevent. On your own subscription, stacks are the right tool and worth an afternoon.

What this means for the assignment

Nothing changes. You still tear down with az resource delete, because the student role on $CLASS_RG is scoped to the resources you create, and a stack at resource-group scope is extra machinery you do not need for one storage account. The value here is recognising the three answers when you meet them:

  1. Incremental (what you used): additive, delete by hand.
  2. Complete: deletes the difference, being phased out, dangerous on shared scopes.
  3. Stacks: the current supported way to manage a group of resources with a real lifecycle.

The HackYourFuture curriculum is licensed under CC BY-NC-SA 4.0 https://hackyourfuture.net/

CC BY-NC-SA 4.0 Icons

Built with ❤️ by the HackYourFuture community · Thank you, contributors

Found a mistake or have a suggestion? Let us know in the feedback form.