From 54d549cb74b39de577d3f1d273f4e9856494b2dc Mon Sep 17 00:00:00 2001 From: zjhe Date: Fri, 8 Jul 2022 17:16:50 +0800 Subject: [PATCH] This patch add support for `disk_encryption_set_id` to harden the cluster's security and solve #194 . This patch should partially solve #183. --- main.tf | 1 + test/fixture/disk_encryption_set.tf | 98 +++++++++++++++++++++++++++++ test/fixture/main.tf | 7 +-- test/fixture/providers.tf | 27 ++++++++ test/fixture/variables.tf | 10 +++ variables.tf | 12 ++-- 6 files changed, 145 insertions(+), 10 deletions(-) create mode 100644 test/fixture/disk_encryption_set.tf create mode 100644 test/fixture/providers.tf diff --git a/main.tf b/main.tf index fd1f5f04..edf0257e 100644 --- a/main.tf +++ b/main.tf @@ -19,6 +19,7 @@ resource "azurerm_kubernetes_cluster" "main" { location = coalesce(var.location, data.azurerm_resource_group.main.location) resource_group_name = data.azurerm_resource_group.main.name node_resource_group = var.node_resource_group + disk_encryption_set_id = var.disk_encryption_set_id dns_prefix = var.prefix sku_tier = var.sku_tier private_cluster_enabled = var.private_cluster_enabled diff --git a/test/fixture/disk_encryption_set.tf b/test/fixture/disk_encryption_set.tf new file mode 100644 index 00000000..49bcbbbf --- /dev/null +++ b/test/fixture/disk_encryption_set.tf @@ -0,0 +1,98 @@ +data "azurerm_client_config" "current" {} + +resource "random_string" "key_vault_prefix" { + length = 6 + special = false + upper = false + numeric = false +} + +data "curl" "public_ip" { + count = var.key_vault_firewall_bypass_ip_cidr == null ? 1 : 0 + http_method = "GET" + uri = "https://api.ipify.org?format=json" +} + +locals { + # We cannot use coalesce here because it's not short-circuit and public_ip's index will cause error + public_ip = var.key_vault_firewall_bypass_ip_cidr == null ? jsondecode(data.curl.public_ip[0].response).ip : var.key_vault_firewall_bypass_ip_cidr +} + +resource "azurerm_key_vault" "des_vault" { + name = "${random_string.key_vault_prefix.result}-des-keyvault" + location = azurerm_resource_group.main.location + resource_group_name = azurerm_resource_group.main.name + tenant_id = data.azurerm_client_config.current.tenant_id + sku_name = "premium" + soft_delete_retention_days = 7 + enabled_for_disk_encryption = true + purge_protection_enabled = true + + network_acls { + bypass = "AzureServices" + default_action = "Deny" + ip_rules = [local.public_ip] + } +} + +resource "azurerm_key_vault_key" "des_key" { + name = "des-key" + key_vault_id = azurerm_key_vault.des_vault.id + key_type = "RSA-HSM" + key_size = 2048 + expiration_date = timeadd("${formatdate("YYYY-MM-DD", timestamp())}T00:00:00Z", "168h") + + key_opts = [ + "decrypt", + "encrypt", + "sign", + "unwrapKey", + "verify", + "wrapKey", + ] + + lifecycle { + ignore_changes = [expiration_date] + } + + depends_on = [ + azurerm_key_vault_access_policy.current_user + ] +} + +resource "azurerm_disk_encryption_set" "des" { + name = "des" + location = azurerm_resource_group.main.location + resource_group_name = azurerm_resource_group.main.name + key_vault_key_id = azurerm_key_vault_key.des_key.id + + identity { + type = "SystemAssigned" + } +} + +resource "azurerm_key_vault_access_policy" "des" { + key_vault_id = azurerm_key_vault.des_vault.id + + tenant_id = azurerm_disk_encryption_set.des.identity.0.tenant_id + object_id = azurerm_disk_encryption_set.des.identity.0.principal_id + + key_permissions = [ + "Get", + "WrapKey", + "UnwrapKey" + ] +} + +resource "azurerm_key_vault_access_policy" "current_user" { + key_vault_id = azurerm_key_vault.des_vault.id + + tenant_id = data.azurerm_client_config.current.tenant_id + object_id = coalesce(var.managed_identity_principal_id, data.azurerm_client_config.current.object_id) + + key_permissions = [ + "Get", + "Create", + "Delete", + ] +} \ No newline at end of file diff --git a/test/fixture/main.tf b/test/fixture/main.tf index a55c7cf9..2a23146e 100644 --- a/test/fixture/main.tf +++ b/test/fixture/main.tf @@ -1,7 +1,3 @@ -provider "azurerm" { - features {} -} - resource "random_id" "prefix" { byte_length = 8 } @@ -39,6 +35,7 @@ module "aks" { network_plugin = "azure" vnet_subnet_id = azurerm_subnet.test.id os_disk_size_gb = 60 + disk_encryption_set_id = azurerm_disk_encryption_set.des.id enable_http_application_routing = true azure_policy_enabled = true enable_host_encryption = true @@ -81,6 +78,7 @@ module "aks_without_monitor" { source = "../.." prefix = "prefix2-${random_id.prefix.hex}" resource_group_name = azurerm_resource_group.main.name + disk_encryption_set_id = azurerm_disk_encryption_set.des.id enable_role_based_access_control = true rbac_aad_managed = true private_cluster_enabled = true @@ -96,6 +94,7 @@ module "aks_cluster_name" { cluster_name = "test-cluster" prefix = "prefix" resource_group_name = azurerm_resource_group.main.name + disk_encryption_set_id = azurerm_disk_encryption_set.des.id enable_role_based_access_control = true rbac_aad_managed = true enable_log_analytics_workspace = true diff --git a/test/fixture/providers.tf b/test/fixture/providers.tf new file mode 100644 index 00000000..f50f8c9a --- /dev/null +++ b/test/fixture/providers.tf @@ -0,0 +1,27 @@ +terraform { + required_providers { + azurerm = { + source = "hashicorp/azurerm" + version = ">=3.11.0" + } + curl = { + source = "anschoewe/curl" + version = "1.0.2" + } + } +} + +provider "curl" {} + +provider "azurerm" { + features { + resource_group { + prevent_deletion_if_contains_resources = false + } + key_vault { + recover_soft_deleted_key_vaults = false + purge_soft_delete_on_destroy = false + purge_soft_deleted_keys_on_destroy = false + } + } +} \ No newline at end of file diff --git a/test/fixture/variables.tf b/test/fixture/variables.tf index 26ffea9b..997b01fa 100644 --- a/test/fixture/variables.tf +++ b/test/fixture/variables.tf @@ -4,3 +4,13 @@ variable "location" { variable "client_id" {} variable "client_secret" {} + +variable "key_vault_firewall_bypass_ip_cidr" { + type = string + default = null +} + +variable "managed_identity_principal_id" { + type = string + default = null +} \ No newline at end of file diff --git a/variables.tf b/variables.tf index 8f808fa5..12c68e3e 100644 --- a/variables.tf +++ b/variables.tf @@ -399,6 +399,12 @@ variable "private_dns_zone_id" { default = null } +variable "disk_encryption_set_id" { + description = "(Optional) The ID of the Disk Encryption Set which should be used for the Nodes and Volumes. More information [can be found in the documentation](https://docs.microsoft.com/azure/aks/azure-disk-customer-managed-keys). Changing this forces a new resource to be created." + type = string + default = null +} + variable "oidc_issuer_enabled" { description = "Enable or Disable the OIDC issuer URL. Defaults to false." type = bool @@ -431,9 +437,3 @@ variable "secret_rotation_interval" { default = "2m" nullable = false } - -variable "local_account_disabled" { - description = "(Optional) - If `true` local accounts will be disabled. Defaults to `false`. See [the documentation](https://docs.microsoft.com/azure/aks/managed-aad#disable-local-accounts) for more information." - type = bool - default = null -} \ No newline at end of file