在 Azure Kubernetes 服务(AKS)群集中启用 KMS 数据加密(预览版)

本文介绍如何在 Azure Kubernetes 服务(AKS)中为 Kubernetes 机密启用密钥管理服务(KMS)数据加密。 KMS 使用 Azure Key Vault 密钥对存储在 etcd 中的 Kubernetes Secrets 进行加密。

AKS 支持两个密钥管理选项:

  • 平台管理的密钥(PMK):AKS 会自动创建和管理加密密钥。 此选项提供最简单的设置和自动密钥轮换。
  • 客户管理的密钥(CMK):创建和管理自己的 Azure Key Vault 和加密密钥。 此选项提供对密钥生命周期的完全控制,并满足强制客户管理的密钥的合规性要求。

有关加密概念和密钥选项的详细信息,请参阅 AKS 的静态数据加密概念

重要

AKS 预览功能可在自助服务和自愿选择的基础上启用。 预览版按“现状”和“视供应情况”提供,它们不包括在服务级别协议和有限保证范围内。 AKS 预览功能是由客户支持尽最大努力部分覆盖。 因此,这些功能并不适合用于生产。 有关详细信息,请参阅以下支持文章:

先决条件

可以使用本地 Azure CLI。

  • 本文需要 Azure CLI 2.73.0 或更高版本。
  • 需要 aks-preview Azure CLI 扩展 版本 19.0.0b13 或更高版本。
    • 如果还没有 aks-preview 扩展,请使用 az extension add 命令安装它。
      az extension add --name aks-preview
      
    • 如果已有 aks-preview 扩展,请使用 az extension update 命令更新它以确保拥有最新版本。
      az extension update --name aks-preview
      
  • kubectl 已安装 CLI 工具。

注册功能标志

若要将 KMS 数据加密与平台管理的密钥配合使用,请在订阅中注册 KMSPMKPreview 功能标志。

  1. 使用 az feature register 命令注册功能标志。

    az feature register --namespace Microsoft.ContainerService --name KMSPMKPreview
    
  2. 使用 az feature show 命令验证注册状态。 几分钟后,状态将显示为“已注册”

    az feature show --namespace Microsoft.ContainerService --name KMSPMKPreview
    
  3. 当状态显示已注册时,请使用命令刷新 az provider register 资源提供程序的注册。

    az provider register --namespace Microsoft.ContainerService
    

设置环境变量

为部署设置环境变量。 将占位符值替换为你自己的值。

# Set environment variables
export SUBSCRIPTION_ID="<your-subscription-id>"
export RESOURCE_GROUP="<your-resource-group>"
export LOCATION="<your-location>"
export CLUSTER_NAME="<your-cluster-name>"

# Set subscription
az account set --subscription $SUBSCRIPTION_ID

# Create resource group if it doesn't exist
az group create --name $RESOURCE_GROUP --location $LOCATION

启用平台管理的密钥加密

使用平台管理的密钥,AKS 会自动创建和管理 Azure Key Vault 和加密密钥。 密钥轮换由平台自动处理。

使用平台管理的密钥创建新的 AKS 群集

使用平台管理的密钥创建具有 KMS 加密的新 AKS 群集。

az aks create \
    --name $CLUSTER_NAME \
    --resource-group $RESOURCE_GROUP \
    --kubernetes-version 1.33.0 \
    --kms-infrastructure-encryption Enabled \
    --generate-ssh-keys

在现有群集上启用平台管理的密钥

在现有 AKS 群集上使用平台管理的密钥启用 KMS 加密。

注释

群集必须运行 Kubernetes 版本 1.33 或更高版本。

az aks update \
    --name $CLUSTER_NAME \
    --resource-group $RESOURCE_GROUP \
    --kms-infrastructure-encryption Enabled

使用私钥保管库启用客户管理的密钥加密

为了增强安全性,可以使用禁用公用网络访问的私钥保管库。 AKS 通过 受信任的服务防火墙例外访问私钥保管库。 本部分介绍如何使用私钥保管库配置客户管理的密钥。

创建具有受信任服务访问权限的密钥保管库和密钥

注释

本部分介绍如何起初创建具有公用网络访问权限的密钥保管库,然后通过受信任服务绕过启用防火墙。 此方法仅用于说明目的。 在生产环境中,您应从一开始就创建和管理您的密钥保管库为私有。 有关管理私钥保管库的指导,请参阅 Azure Key Vault 网络安全

  1. 创建启用了 Azure RBAC 的密钥保管库。

    export KEY_VAULT_NAME="<your-key-vault-name>"
    
    az keyvault create \
        --name $KEY_VAULT_NAME \
        --resource-group $RESOURCE_GROUP \
        --enable-rbac-authorization true \
        --public-network-access Enabled
    
    # Get the key vault resource ID
    export KEY_VAULT_RESOURCE_ID=$(az keyvault show --name $KEY_VAULT_NAME --resource-group $RESOURCE_GROUP --query id -o tsv)
    
  2. 为自己分配 Key Vault Crypto Officer 角色以创建密钥。

    az role assignment create \
        --role "Key Vault Crypto Officer" \
        --assignee-object-id $(az ad signed-in-user show --query id -o tsv) \
        --assignee-principal-type "User" \
        --scope $KEY_VAULT_RESOURCE_ID
    
  3. 在密钥保管库中创建密钥。

    export KEY_NAME="<your-key-name>"
    
    az keyvault key create --name $KEY_NAME --vault-name $KEY_VAULT_NAME
    
    # Get the key ID (without version for automatic rotation)
    export KEY_ID=$(az keyvault key show --name $KEY_NAME --vault-name $KEY_VAULT_NAME --query 'key.kid' -o tsv)
    export KEY_ID_NO_VERSION=$(echo $KEY_ID | sed 's|/[^/]*$||')
    
  4. 启用密钥保管库防火墙并允许受信任的服务绕过。

    az keyvault update \
        --name $KEY_VAULT_NAME \
        --resource-group $RESOURCE_GROUP \
        --default-action Deny \
        --bypass AzureServices
    

    --default-action Deny 参数会阻止公用网络访问,并且 --bypass AzureServices 该参数允许受信任的 Azure 服务(包括 AKS)访问密钥保管库。

创建用户分配的托管标识

  1. 为群集创建用户分配的托管标识。

    export IDENTITY_NAME="<your-identity-name>"
    
    az identity create --name $IDENTITY_NAME --resource-group $RESOURCE_GROUP
    
    # Get the identity details
    export IDENTITY_OBJECT_ID=$(az identity show --name $IDENTITY_NAME --resource-group $RESOURCE_GROUP --query 'principalId' -o tsv)
    export IDENTITY_RESOURCE_ID=$(az identity show --name $IDENTITY_NAME --resource-group $RESOURCE_GROUP --query 'id' -o tsv)
    
  2. 将所需的角色分配给托管标识。

    # Assign Key Vault Crypto User role for encrypt/decrypt operations
    az role assignment create \
        --role "Key Vault Crypto User" \
        --assignee-object-id $IDENTITY_OBJECT_ID \
        --assignee-principal-type "ServicePrincipal" \
        --scope $KEY_VAULT_RESOURCE_ID
    
    # Assign Key Vault Contributor role for key management
    az role assignment create \
        --role "Key Vault Contributor" \
        --assignee-object-id $IDENTITY_OBJECT_ID \
        --assignee-principal-type "ServicePrincipal" \
        --scope $KEY_VAULT_RESOURCE_ID
    

使用客户管理的密钥(专用)创建新的 AKS 群集

使用客户管理的密钥和私钥保管库创建具有 KMS 加密的新 AKS 群集。

az aks create \
    --name $CLUSTER_NAME \
    --resource-group $RESOURCE_GROUP \
    --kubernetes-version 1.33.0 \
    --kms-infrastructure-encryption Enabled \
    --enable-azure-keyvault-kms \
    --azure-keyvault-kms-key-id $KEY_ID_NO_VERSION \
    --azure-keyvault-kms-key-vault-resource-id $KEY_VAULT_RESOURCE_ID \
    --azure-keyvault-kms-key-vault-network-access Private \
    --assign-identity $IDENTITY_RESOURCE_ID \
    --generate-ssh-keys

在现有群集上启用客户管理的密钥(专用)

使用现有 AKS 群集上的私钥保管库,通过客户管理的密钥启用 KMS 加密。

注释

群集必须运行 Kubernetes 版本 1.33 或更高版本。

az aks update \
    --name $CLUSTER_NAME \
    --resource-group $RESOURCE_GROUP \
    --kms-infrastructure-encryption Enabled \
    --enable-azure-keyvault-kms \
    --azure-keyvault-kms-key-id $KEY_ID_NO_VERSION \
    --azure-keyvault-kms-key-vault-resource-id $KEY_VAULT_RESOURCE_ID \
    --azure-keyvault-kms-key-vault-network-access Private \
    --assign-identity $IDENTITY_RESOURCE_ID

使用公钥保管库启用客户管理的密钥加密

使用客户管理的密钥,可以创建和管理自己的 Azure Key Vault 和加密密钥。 本部分介绍如何使用公钥保管库配置客户管理的密钥。

创建密钥保管库和密钥

  1. 创建启用了 Azure RBAC 的密钥保管库。

    export KEY_VAULT_NAME="<your-key-vault-name>"
    
    az keyvault create \
        --name $KEY_VAULT_NAME \
        --resource-group $RESOURCE_GROUP \
        --enable-rbac-authorization true \
        --public-network-access Enabled
    
    # Get the key vault resource ID
    export KEY_VAULT_RESOURCE_ID=$(az keyvault show --name $KEY_VAULT_NAME --resource-group $RESOURCE_GROUP --query id -o tsv)
    
  2. 为自己分配 Key Vault Crypto Officer 角色以创建密钥。

    az role assignment create \
        --role "Key Vault Crypto Officer" \
        --assignee-object-id $(az ad signed-in-user show --query id -o tsv) \
        --assignee-principal-type "User" \
        --scope $KEY_VAULT_RESOURCE_ID
    
  3. 在密钥保管库中创建密钥。

    export KEY_NAME="<your-key-name>"
    
    az keyvault key create --name $KEY_NAME --vault-name $KEY_VAULT_NAME
    
    # Get the key ID (without version for automatic rotation)
    export KEY_ID=$(az keyvault key show --name $KEY_NAME --vault-name $KEY_VAULT_NAME --query 'key.kid' -o tsv)
    export KEY_ID_NO_VERSION=$(echo $KEY_ID | sed 's|/[^/]*$||')
    

创建用户分配的托管标识

  1. 为群集创建用户分配的托管标识。

    export IDENTITY_NAME="<your-identity-name>"
    
    az identity create --name $IDENTITY_NAME --resource-group $RESOURCE_GROUP
    
    # Get the identity details
    export IDENTITY_OBJECT_ID=$(az identity show --name $IDENTITY_NAME --resource-group $RESOURCE_GROUP --query 'principalId' -o tsv)
    export IDENTITY_RESOURCE_ID=$(az identity show --name $IDENTITY_NAME --resource-group $RESOURCE_GROUP --query 'id' -o tsv)
    
  2. 将所需的角色分配给托管标识。

    # Assign Key Vault Crypto User role for encrypt/decrypt operations
    az role assignment create \
        --role "Key Vault Crypto User" \
        --assignee-object-id $IDENTITY_OBJECT_ID \
        --assignee-principal-type "ServicePrincipal" \
        --scope $KEY_VAULT_RESOURCE_ID
    
    # Assign Key Vault Contributor role for key management
    az role assignment create \
        --role "Key Vault Contributor" \
        --assignee-object-id $IDENTITY_OBJECT_ID \
        --assignee-principal-type "ServicePrincipal" \
        --scope $KEY_VAULT_RESOURCE_ID
    

使用客户管理的密钥创建新的 AKS 群集

使用客户管理的密钥创建具有 KMS 加密的新 AKS 群集。

az aks create \
    --name $CLUSTER_NAME \
    --resource-group $RESOURCE_GROUP \
    --kubernetes-version 1.33.0 \
    --kms-infrastructure-encryption Enabled \
    --enable-azure-keyvault-kms \
    --azure-keyvault-kms-key-id $KEY_ID_NO_VERSION \
    --azure-keyvault-kms-key-vault-resource-id $KEY_VAULT_RESOURCE_ID \
    --azure-keyvault-kms-key-vault-network-access Public \
    --assign-identity $IDENTITY_RESOURCE_ID \
    --generate-ssh-keys

在现有群集上启用客户管理的密钥

在现有 AKS 群集上使用客户管理的密钥启用 KMS 加密。

注释

群集必须运行 Kubernetes 版本 1.33 或更高版本。

az aks update \
    --name $CLUSTER_NAME \
    --resource-group $RESOURCE_GROUP \
    --kms-infrastructure-encryption Enabled \
    --enable-azure-keyvault-kms \
    --azure-keyvault-kms-key-id $KEY_ID_NO_VERSION \
    --azure-keyvault-kms-key-vault-resource-id $KEY_VAULT_RESOURCE_ID \
    --azure-keyvault-kms-key-vault-network-access Public \
    --assign-identity $IDENTITY_RESOURCE_ID

验证 KMS 配置

启用 KMS 加密后,请验证配置。

az aks show --name $CLUSTER_NAME --resource-group $RESOURCE_GROUP --query 'securityProfile'

输出内容展示了 KMS 配置:

{
    "azureKeyVaultKms": {
        "enabled": true,
        "keyId": "https://<key-vault-name>.vault.azure.cn/keys/<key-name>",
        "keyVaultNetworkAccess": "Public",
        "keyVaultResourceId": "<key-vault-resource-id>"
    },
    "kubernetesResourceObjectEncryptionProfile": {
        "infrastructureEncryption": "Enabled"
    }
}

在密钥管理选项之间迁移

可以在平台管理的密钥和客户管理的密钥之间迁移。

从平台管理的密钥迁移到客户管理的密钥

若要从平台管理的密钥迁移到客户管理的密钥,请先设置密钥保管库、密钥和托管标识,如客户管理的密钥部分所述,然后运行更新命令:

az aks update \
    --name $CLUSTER_NAME \
    --resource-group $RESOURCE_GROUP \
    --kms-infrastructure-encryption Enabled \
    --enable-azure-keyvault-kms \
    --azure-keyvault-kms-key-id $KEY_ID_NO_VERSION \
    --azure-keyvault-kms-key-vault-resource-id $KEY_VAULT_RESOURCE_ID \
    --azure-keyvault-kms-key-vault-network-access Public \
    --assign-identity $IDENTITY_RESOURCE_ID

从客户管理的密钥迁移到平台管理的密钥

若要从客户管理的密钥迁移到平台管理的密钥,请执行以下作:

az aks update \
    --name $CLUSTER_NAME \
    --resource-group $RESOURCE_GROUP \
    --kms-infrastructure-encryption Enabled \
    --disable-azure-keyvault-kms

密钥轮换

使用 KMS 数据加密时,密钥轮换的处理方式因密钥管理选项而异:

  • 平台管理的密钥:密钥轮换是自动的。 无需执行任何操作。
  • 客户管理的密钥:在 Azure Key Vault 中轮换密钥版本时,KMS 控制器会定期(每 6 小时)检测轮换,并使用新的密钥版本。

注释

与旧版 KMS 体验不同,使用此新实现,无需在密钥轮换后手动重新加密机密。 平台会自动处理此问题。