Authenticating to AKS cluster on Active Directory via Terraform Kubernetes provider

Azure AKS authentication with Active Directory (Entra) is a one of the most preferred option for a production AKS workload. The seamless integration makes managing roles and users very easy.

If you have created your AKS cluster using Terraform  you might have faced difficulty authenticating to your cluster. Since, our cluster is using Active Directory normal provider configuration do not work, with the help of  Kubelogin  we can utilise Entra credentials and authenticate to the cluster.

Prerequisites:

  1. Azure CLI installed.
  2. Kubelogin installed

The process is described in the diagram below.

  1. Terraform uses the KubeLogin to do the heavy lifting of fetching credentials from Active Directory.
  2. The Object which it fetches is the one currently logged in.
  3. Once, the credentials are fetched it authenticates to the cluster.

 

data "azurerm_kubernetes_cluster" "main" {
  name                = module.aks.aks_name
  resource_group_name = "aks-cluster-rg"
}

data "azurerm_subscription" "current" {}

provider "kubernetes" {
  host                   = data.azurerm_kubernetes_cluster.main.kube_config.0.host
  cluster_ca_certificate = base64decode(data.azurerm_kubernetes_cluster.main.kube_config.0.cluster_ca_certificate)

  exec {
    api_version = "client.authentication.k8s.io/v1beta1"
    command     = "kubelogin"
    args = [
      "get-token",
      "--login",
      "azurecli",
      "--environment",
      "AzurePublicCloud",
      "--tenant-id",
      data.azurerm_subscription.current.tenant_id,
      "--server-id",
      "6dae42f8-4368-4678-94ff-3960e28e3630", #
      "|",
      "jq",
      ".status.token"
    ]
  }
}

Terraform provides the exec command. The exec command runs before the provider API call to connect to the cluster.

We are passing “kubelogin” to the command parameter. This means to execute the kubelogin CLI  and pass the relevant arguments.

Server ID is hard-coded because it will never change as it’s the Azure Kubernetes Service AAD Server.

Sequence flow on how does Terraform uses the Kubelogin to fetch credentials from Active Directory before connecting to the K8 cluster

Before running Terraform, we must be authenticated to Azure. This can be easily achieved by using the az cli

az login

Github workflow can leverage Azure OpenID which makes it more secure and you don’t need to store credentials such as Service Principal secret.

I highly recommend using OpenID for your pipeline!

To verify our authentication we can simply display out all our namespaces.

data "kubernetes_all_namespaces" "this" {}

If you have successfully connected to the cluster, there won’t be any errors.

Key point:

The app role must have a role assigned for Azure Kubernetes like: “Azure Kubernetes Service RBAC Admin” or any role that allow reading Namespaces.

Contributor role does not work!