Learning Kubernetes part 2 - build AKS

Last time we setup some Terraform and Azure configuration for the build of an Azure Kubernetes Service lab in Azure. I put together the Terraform and a Resource Group in Azure.

This time, I am going to share the Terraform for an Azure Kubernetes Cluster. Nothing super fancy, but a lab type environment. I chose this method because I am working in cloud technologies and wish to learn how the cloud providers do it.

I know that Kubernetes is ubiquitous in many ways, where it runs on the laptop or local lab the same way as it might in the cloud. Mostly, this is true, but AKS brings the management and control plane nodes to the cloud platform. Read more about that here.

The Terraform for AKS

Using Terraform to build this lab environment has been great. It is fairly easy/straightforward to learn and the documentation is pretty solid too.

Note: The Kubernetes configuration can be fairly large depending on the size of your environment. Here, because this is for a lab, I tried to keep things small and manageable.

resource "azurerm_kubernetes_cluster" "this" {
  name                = module.naming.kubernetes_cluster.name
  resource_group_name = azurerm_resource_group.this.name
  location            = azurerm_resource_group.this.location

  dns_prefix = "woot"

  automatic_channel_upgrade = "stable"

  ingress_application_gateway {
    subnet_id = azurerm_subnet.appgw.id
    #subnet_id = data.azurerm_subnet.appgw_subnet.id

  default_node_pool {
    name            = "default"
    node_count      = 2
    vm_size         = "standard_D2_V2"
    os_disk_size_gb = "80"
    os_disk_type    = "Managed"


  identity {
    type = "SystemAssigned"

  tags = local.tags


Let’s walk through the code above. It creates an Azure Kubernetes Cluster resource with the name “this”. Generally, I do not like using abstract naming for resources. Using “this” in Terraform to call out your resource is for Terraform only. When I name resources many times, I will use the resource type for the name:

Resource “azurerm_kubernetes_cluster” “aks”

There are some blogs online that call out the redundancy with this approach and that is fine. I like my code to be as readable as possible when using it as I go forward. Since this is only for terraform, the naming should be easy for the user/developer/code writer. </rant>

Back to the code above…

  • Name - the name of the resource being deployed to Azure - using the Azure Naming module
  • Resource Group Name - the name of the resource group this AKS instance will be created in.
  • Location - the region where the AKS resource will be created in
  • dns_prefix - a prefix for your AKS API server DNS name
  • automatic_channel_upgrade - AKS can be upgraded automatically by Azure, this chooses the branch to use for these upgraded - in this scenario I chose stable for auto upgrade
  • ingress_application_gateway - this specifies the ingress to be an application gateway in Azure rather than an Nginx ingress that lives within Kubernetes. This uses an add-on for AKS to allow K8s to control the resource in this case. Using a helm configuration to setup Application Gateway Ingress if your environment needs more control, or specify an existing App Gateway created by Terraform. More information on the helm configuration can be found here.
    • subnet_id - the subnet ID for the resource of the subnet where the app gateway will exist._
  • default_node_pool - a definition of resources to be used as the default. If no other node pool blocks are setup, this will be used for nodes within the cluster
    • node_count - the number of nodes within the cluster_
    • vm_size - the Azure VMs to use for the cluster_
    • os_disk_size - the size of the OS disk within the virtual machines
    • disk_type - ephemeral (deleted when the nodes reboot) or managed (managed by Azure but will survive a restart)_
    • node_count - how many nodes will exist in this cluster_
  • identity - an object ID for use by the AKS resource, if SystemAssigned Azure will manage the object ID and password for the resource. If UserAssigned is chosen here, managing the object id and password for the service account will fall on the user/customer. SystemAssigned is preferred. More information around managed system identity can be found here.
  • tags - tags in Azure are for taxonomy only, they help organize resources - they do not, today, produce actions or firewall rules as they might in other platforms.

There are many other options available that can be set with Terraform, but for a small lab just to learn, these defaults seem to work well for me. A better list of the options available for building Kubernetes clusters in Azure can be found here.

Next Time - Key Vault

The next installment of this series will go through the configuration of Azure Key Vault and a secret to hold the Kubeconfig for the AKS cluster we looked at here.

Once we have a few resources outlined, we can run the terraform code to build these and see what might happen. I am deliberately waiting to have a few things to create just so we can see what it looks like to create these things all at once.

Written on July 7, 2022