Skip to content

Commit 713cbfc

Browse files
committed
Add quickstart sample for private AKS cluster with custom DNS
1 parent cc6b61a commit 713cbfc

File tree

7 files changed

+234
-0
lines changed

7 files changed

+234
-0
lines changed
Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
# Private Azure Kubernetes Service with Custom DNS Server
2+
3+
This template deploys a private Azure Kubernetes Service cluster configured with custom DNS server. A new VNet with provided
4+
custom DNS server would be provisioned and the AKS cluster is deployed into this new VNet. The DNS server's VNet would
5+
also be linked to AKS provisioned private DNS zone, so that AKS cluster's private FQDN could be resolved successfully on
6+
custom DNS server.
7+
8+
To use this template, ensure the following pre-requirements have been set:
9+
10+
* Azure CLI and terraform installed locally
11+
* Pre-configure DNS servers outside of AKS VNet
12+
* Forward AKS cluster FQDN `azmk8s.io` (or only private cluster FQDN `privatelink.<region>.azmk8s.io`) to Azure DNS `168.63.129.16`
13+
* Get the DNS servers IP address, which would be set in `custom_dns`
14+
* Get the DNS server's VNet resource ID, which would be set in `custom_dns_vnet_id`
15+
16+
## Resources
17+
18+
| Terraform Resource Type | Description |
19+
|-------------------------|-------------|
20+
| `azurerm_resource_group` | The resource group all resources are deployed into |
21+
| `azurerm_virtual_network` | The VNet that AKS cluster would be deployed on |
22+
| `azurerm_subnet` | The subnet that AKS cluster would be deployed on |
23+
| `azurerm_kubernetes_cluster` | The AKS cluster |
24+
| `null_resource.dns_zone_link` | Link custom DNS server's VNet to AKS private DNS zone|
25+
26+
## Variables
27+
28+
| Name | Description |
29+
|------|-------------|
30+
| `resource_group_name` | Name of the Azure resource group|
31+
| `cluster_name` | Name of the AKS cluster|
32+
| `custom_dns` | IP of custom DNS server|
33+
| `custom_dns_vnet_id` |Resource ID of the Azure VNet that holds custom DNS server|
34+
| `client_id` | The service principal ID|
35+
| `client_secret` | The service principal password|
36+
| `agent_count` | The number of K8S nodes to provision|
37+
| `kubernetes_version` | The version of K8S to provision|
38+
| `ssh_public_key` | The SSH public key of K8S nodes |
39+
| `dns_prefix` | The DNS prefix of AKS cluster |
40+
| `location` | The location of Azure resources |
41+
42+
## Usage
43+
44+
```sh
45+
terraform plan \
46+
-var 'resource_group_name=aks-quickstart' \
47+
-var 'cluster_name=aks' \
48+
-var 'custom_dns=<your-custom-dns-IP>' \
49+
-var 'custom_dns_vnet_id=<your-custom-dns-vnet-id>' \
50+
-var 'client_id=<your-client-id>' \
51+
-var 'client_secret=<your-client-secret>' \
52+
-out demo.tfplan
53+
54+
terraform apply demo.tfplan
55+
```
Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
resource "azurerm_resource_group" "k8s" {
2+
name = "${var.resource_group_name}"
3+
location = "${var.location}"
4+
}
5+
6+
resource "azurerm_virtual_network" "myvnet" {
7+
name = "myvnet"
8+
location = "${azurerm_resource_group.k8s.location}"
9+
resource_group_name = "${azurerm_resource_group.k8s.name}"
10+
address_space = ["10.240.0.0/16"]
11+
dns_servers = ["${var.custom_dns}"]
12+
}
13+
14+
resource "azurerm_subnet" "mysubnet" {
15+
name = "mysubnet"
16+
resource_group_name = "${azurerm_resource_group.k8s.name}"
17+
address_prefixes = ["10.240.10.0/24"]
18+
virtual_network_name = "${azurerm_virtual_network.myvnet.name}"
19+
}
20+
21+
resource "azurerm_kubernetes_cluster" "k8s" {
22+
name = "${var.cluster_name}"
23+
location = "${azurerm_resource_group.k8s.location}"
24+
resource_group_name = "${azurerm_resource_group.k8s.name}"
25+
dns_prefix = "${var.dns_prefix}"
26+
kubernetes_version = "${var.kubernetes_version}"
27+
private_cluster_enabled = true
28+
29+
linux_profile {
30+
admin_username = "azureuser"
31+
32+
ssh_key {
33+
key_data = "${file("${var.ssh_public_key}")}"
34+
}
35+
}
36+
37+
default_node_pool {
38+
name = "agentpool1"
39+
node_count = "${var.agent_count}"
40+
vm_size = "Standard_D2_v3"
41+
os_disk_size_gb = 30
42+
vnet_subnet_id = "${azurerm_subnet.mysubnet.id}"
43+
}
44+
45+
service_principal {
46+
client_id = "${var.client_id}"
47+
client_secret = "${var.client_secret}"
48+
}
49+
50+
network_profile {
51+
network_plugin = "azure"
52+
load_balancer_sku = "standard"
53+
}
54+
55+
}
Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
#!/bin/bash
2+
# Query AKS private DNS zone and then link it to custom DNS VNet.
3+
set -e
4+
5+
wait-for-node-resource-group() {
6+
NODE_RESOURCE_GROUP=$(az aks show -g ${AKS_RESOURCE_GROUP} -n ${AKS_CLUSTER_NAME} -o json 2>/dev/null | jq -r '.nodeResourceGroup')
7+
while [ "${NODE_RESOURCE_GROUP}" == "" ]; do
8+
echo "Waiting for node resource group..."
9+
sleep 5
10+
NODE_RESOURCE_GROUP=$(az aks show -g ${AKS_RESOURCE_GROUP} -n ${AKS_CLUSTER_NAME} -o json 2>/dev/null | jq -r '.nodeResourceGroup')
11+
done
12+
}
13+
14+
wait-for-private-dns-zone() {
15+
length=$(az network private-dns zone list -g ${NODE_RESOURCE_GROUP} -o json 2>/dev/null | jq '. | length')
16+
while [[ $length -eq 0 ]]; do
17+
echo "Waiting for private DNS zone..."
18+
sleep 5
19+
length=$(az network private-dns zone list -g ${NODE_RESOURCE_GROUP} -o json 2>/dev/null | jq '. | length')
20+
done
21+
}
22+
23+
wait-for-node-resource-group
24+
NODE_RESOURCE_GROUP=$(az aks show -g ${AKS_RESOURCE_GROUP} -n ${AKS_CLUSTER_NAME} -o json 2>/dev/null | jq -r '.nodeResourceGroup')
25+
wait-for-private-dns-zone
26+
ZONE_NAME=$(az network private-dns zone list -g ${NODE_RESOURCE_GROUP} -o json | jq -r '.[0].name')
27+
echo "Get the private DNS Zone ${ZONE_NAME}"
28+
az network private-dns link vnet create -o json \
29+
-g ${NODE_RESOURCE_GROUP} \
30+
-n private-dns-link \
31+
--registration-enabled false \
32+
--zone-name ${ZONE_NAME} \
33+
--virtual-network ${DNS_VNET}
34+
35+
echo "Private DNS Zone ${ZONE_NAME} has been linked to VNet ${DNS_VNET}."
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
resource "null_resource" "dns_zone_link" {
2+
3+
provisioner "local-exec" {
4+
interpreter = ["bash"]
5+
command = "dns-zone-link.sh"
6+
7+
environment = {
8+
DNS_VNET = "${var.custom_dns_vnet_id}"
9+
AKS_RESOURCE_GROUP="${var.resource_group_name}"
10+
AKS_CLUSTER_NAME="${var.cluster_name}"
11+
}
12+
}
13+
}
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
provider "azurerm" {
2+
version = "~>2.11"
3+
features {}
4+
}
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
output "kube_config" {
2+
value = "${azurerm_kubernetes_cluster.k8s.kube_config_raw}"
3+
}
4+
5+
output "host" {
6+
value = "${azurerm_kubernetes_cluster.k8s.kube_config.0.host}"
7+
}
Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,65 @@
1+
variable resource_group_name {
2+
type = string
3+
description = "Name of the Azure resource group"
4+
default = "aks-quickstart"
5+
}
6+
7+
variable cluster_name {
8+
type = string
9+
description = "Name of the AKS cluster"
10+
default = "demo-private"
11+
}
12+
13+
variable custom_dns {
14+
type = string
15+
description = "IP of custom DNS server"
16+
default = "168.63.129.16"
17+
}
18+
19+
variable custom_dns_vnet_id {
20+
type = string
21+
description = "Resource ID of the Azure VNet that holds custom DNS server"
22+
default = ""
23+
}
24+
25+
variable "client_id" {
26+
type = string
27+
description = "The service principal ID"
28+
default = "<client-id>"
29+
}
30+
31+
variable "client_secret" {
32+
type = string
33+
description = "The service principal password"
34+
default = "<client-secret>"
35+
}
36+
37+
variable "agent_count" {
38+
type = string
39+
description = "The number of K8S nodes to provision"
40+
default = 3
41+
}
42+
43+
variable "kubernetes_version" {
44+
type = string
45+
description = "The version of K8S to provision"
46+
default = "1.17.9"
47+
}
48+
49+
variable "ssh_public_key" {
50+
type = string
51+
description = "The SSH public key of K8S nodes"
52+
default = "~/.ssh/id_rsa.pub"
53+
}
54+
55+
variable "dns_prefix" {
56+
type = string
57+
description = "The DNS prefix"
58+
default = "aks"
59+
}
60+
61+
variable location {
62+
type = string
63+
description = "The location"
64+
default = "East US"
65+
}

0 commit comments

Comments
 (0)