Share via


Azure Key Vault 비밀 공급자 확장을 사용하여 Azure Arc 지원 Kubernetes 클러스터로 비밀 가져오기

비밀 저장소 CSI 드라이버용 Azure Key Vault 공급자를 사용하면 CSI 볼륨을 통해 Kubernetes 클러스터와 비밀 저장소로 Azure Key Vault를 통합할 수 있습니다. Azure Arc 지원 Kubernetes 클러스터의 경우 Azure Key Vault 비밀 공급자 확장을 설치하여 비밀을 가져올 수 있습니다.

Azure Key Vault 비밀 공급자 확장의 기능은 다음과 같습니다.

  • CSI 인라인 볼륨을 사용하여 Pod에 비밀/키/인증서 탑재
  • SecretProviderClass CRD를 사용하여 Pod 이식성 지원
  • Linux 및 Windows 컨테이너 지원
  • Kubernetes 비밀과의 동기화 지원
  • 비밀의 자동 회전 지원
  • 확장 구성 요소는 가용성 영역에 배포되어 영역 중복을 만듭니다.

필수 조건

  • 이미 Azure Arc에 연결된 지원되는 Kubernetes 배포판이 있는 클러스터입니다. 이 시나리오에 대해 현재 지원되는 Kubernetes 배포는 다음과 같습니다.
    • Cluster API Azure
    • Azure Stack HCI의 AKS(Azure Kubernetes Service)
    • Azure Arc 지원 AKS
    • Google Kubernetes Engine
    • OpenShift Kubernetes Distribution
    • Canonical Kubernetes Distribution
    • Elastic Kubernetes Service
    • Tanzu Kubernetes Grid
    • Azure Red Hat OpenShift
  • 클러스터 확장에 대한 일반적인 필수 구성 요소가 충족되어야 합니다. k8s-extension Azure CLI 확장 버전 0.4.0 이상을 사용해야 합니다.

Arc 지원 Kubernetes 클러스터에 Azure Key Vault 비밀 공급자 확장 설치

Azure Portal에서 Azure CLI를 사용하거나 ARM 템플릿을 배포하여 연결된 클러스터에 Azure Key Vault 비밀 공급자 확장을 설치할 수 있습니다.

각 Azure Arc 지원 Kubernetes 클러스터에는 확장의 인스턴스를 하나만 배포할 수 있습니다.

클러스터가 아웃바운드 프록시 서버 뒤에 있는 경우 확장을 설치하기 전에 프록시 구성 옵션을 사용하여 Azure Arc에 연결해야 합니다.

Azure Portal

  1. Azure Portal에서 Kubernetes - Azure Arc로 이동하여 클러스터를 선택합니다.

  2. 설정에서 확장을 선택한 다음, + 추가를 선택합니다.

    Screenshot showing the Extensions page for an Arc-enabled Kubernetes cluster in the Azure portal.

  3. 사용 가능한 확장 목록에서 Azure Key Vault 비밀 공급자를 선택하여 최신 버전의 확장을 배포합니다.

    Screenshot of the Azure Key Vault Secrets Provider extension in the Azure portal.

  4. 표시되는 메시지에 따라 확장을 배포합니다. 필요한 경우 구성 탭에서 기본 옵션을 변경하여 설치를 사용자 지정합니다.

Azure CLI

  1. 환경 변수를 설정합니다.

    export CLUSTER_NAME=<arc-cluster-name>
    export RESOURCE_GROUP=<resource-group-name>
    
  2. 다음 명령을 실행하여 비밀 저장소 CSI 드라이버 및 Azure Key Vault 비밀 공급자 확장을 설치합니다.

    az k8s-extension create --cluster-name $CLUSTER_NAME --resource-group $RESOURCE_GROUP --cluster-type connectedClusters --extension-type Microsoft.AzureKeyVaultSecretsProvider --name akvsecretsprovider
    

다음 예시와 유사한 출력이 표시됩니다. 비밀 공급자 Helm 차트가 클러스터에 배포되기까지 몇 분 정도 걸릴 수 있습니다.

{
  "aksAssignedIdentity": null,
  "autoUpgradeMinorVersion": true,
  "configurationProtectedSettings": {},
  "configurationSettings": {},
  "customLocationSettings": null,
  "errorInfo": null,
  "extensionType": "microsoft.azurekeyvaultsecretsprovider",
  "id": "/subscriptions/xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx/resourceGroups/$RESOURCE_GROUP/providers/Microsoft.Kubernetes/connectedClusters/$CLUSTER_NAME/providers/Microsoft.KubernetesConfiguration/extensions/akvsecretsprovider",
  "identity": {
    "principalId": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
    "tenantId": null,
    "type": "SystemAssigned"
  },
  "location": null,
  "name": "akvsecretsprovider",
  "packageUri": null,
  "provisioningState": "Succeeded",
  "releaseTrain": "Stable",
  "resourceGroup": "$RESOURCE_GROUP",
  "scope": {
    "cluster": {
      "releaseNamespace": "kube-system"
    },
    "namespace": null
  },
  "statuses": [],
  "systemData": {
    "createdAt": "2022-05-12T18:35:56.552889+00:00",
    "createdBy": null,
    "createdByType": null,
    "lastModifiedAt": "2022-05-12T18:35:56.552889+00:00",
    "lastModifiedBy": null,
    "lastModifiedByType": null
  },
  "type": "Microsoft.KubernetesConfiguration/extensions",
  "version": "1.1.3"
}

ARM 템플릿

  1. 다음 형식을 사용하여 .json 파일을 만듭니다. 클러스터를 나타내도록 <cluster-name> 값을 업데이트해야 합니다.

    {
        "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
        "contentVersion": "1.0.0.0",
        "parameters": {
            "ConnectedClusterName": {
                "defaultValue": "<cluster-name>",
                "type": "String",
                "metadata": {
                    "description": "The Connected Cluster name."
                }
            },
            "ExtensionInstanceName": {
                "defaultValue": "akvsecretsprovider",
                "type": "String",
                "metadata": {
                    "description": "The extension instance name."
                }
            },
            "ExtensionVersion": {
                "defaultValue": "",
                "type": "String",
                "metadata": {
                    "description": "The version of the extension type."
                }
            },
            "ExtensionType": {
                "defaultValue": "Microsoft.AzureKeyVaultSecretsProvider",
                "type": "String",
                "metadata": {
                    "description": "The extension type."
                }
            },
            "ReleaseTrain": {
                "defaultValue": "stable",
                "type": "String",
                "metadata": {
                    "description": "The release train."
                }
            }
        },
        "functions": [],
        "resources": [
            {
                "type": "Microsoft.KubernetesConfiguration/extensions",
                "apiVersion": "2021-09-01",
                "name": "[parameters('ExtensionInstanceName')]",
                "identity": {
                 "type": "SystemAssigned"
                },
                "properties": {
                    "extensionType": "[parameters('ExtensionType')]",
                    "releaseTrain": "[parameters('ReleaseTrain')]",
                    "version": "[parameters('ExtensionVersion')]"
                },
                "scope": "[concat('Microsoft.Kubernetes/connectedClusters/', parameters('ConnectedClusterName'))]"
            }
        ]
    }
    
  2. 이제 다음 Azure CLI 명령을 사용하여 환경 변수를 설정합니다.

    export TEMPLATE_FILE_NAME=<template-file-path>
    export DEPLOYMENT_NAME=<desired-deployment-name>
    
  3. 마지막으로 이 Azure CLI 명령을 실행하여 Azure Key Vault 비밀 공급자 확장을 설치합니다.

    az deployment group create --name $DEPLOYMENT_NAME --resource-group $RESOURCE_GROUP --template-file $TEMPLATE_FILE_NAME
    

이제 비밀 공급자 리소스가 표시되고 클러스터에서 확장을 사용할 수 있습니다.

확장 설치 유효성 검사

Azure Key Vault 비밀 공급자 확장의 성공적인 설치를 확인하려면 다음 명령을 실행합니다.

az k8s-extension show --cluster-type connectedClusters --cluster-name $CLUSTER_NAME --resource-group $RESOURCE_GROUP --name akvsecretsprovider

다음 예시와 유사한 출력이 표시됩니다.

{
  "aksAssignedIdentity": null,
  "autoUpgradeMinorVersion": true,
  "configurationProtectedSettings": {},
  "configurationSettings": {},
  "customLocationSettings": null,
  "errorInfo": null,
  "extensionType": "microsoft.azurekeyvaultsecretsprovider",
  "id": "/subscriptions/xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx/resourceGroups/$RESOURCE_GROUP/providers/Microsoft.Kubernetes/connectedClusters/$CLUSTER_NAME/providers/Microsoft.KubernetesConfiguration/extensions/akvsecretsprovider",
  "identity": {
    "principalId": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
    "tenantId": null,
    "type": "SystemAssigned"
  },
  "location": null,
  "name": "akvsecretsprovider",
  "packageUri": null,
  "provisioningState": "Succeeded",
  "releaseTrain": "Stable",
  "resourceGroup": "$RESOURCE_GROUP",
  "scope": {
    "cluster": {
      "releaseNamespace": "kube-system"
    },
    "namespace": null
  },
  "statuses": [],
  "systemData": {
    "createdAt": "2022-05-12T18:35:56.552889+00:00",
    "createdBy": null,
    "createdByType": null,
    "lastModifiedAt": "2022-05-12T18:35:56.552889+00:00",
    "lastModifiedBy": null,
    "lastModifiedByType": null
  },
  "type": "Microsoft.KubernetesConfiguration/extensions",
  "version": "1.1.3"
}

Azure Key Vault 만들기 또는 선택

다음으로, 연결된 클러스터에서 사용할 Azure Key Vault를 지정합니다. 아직 없는 경우 다음 명령을 사용하여 새 Key Vault를 만듭니다. 키 자격 증명 모음의 이름은 전역적으로 고유해야 합니다.

다음 환경 변수를 설정합니다.

export AKV_RESOURCE_GROUP=<resource-group-name>
export AZUREKEYVAULT_NAME=<AKV-name>
export AZUREKEYVAULT_LOCATION=<AKV-location>

다음 명령을 실행합니다.

az keyvault create -n $AZUREKEYVAULT_NAME -g $AKV_RESOURCE_GROUP -l $AZUREKEYVAULT_LOCATION

Azure Key Vault는 키, 비밀 및 인증서를 저장할 수 있습니다. 이 예제에서는 다음 명령을 사용하여 DemoSecret라는 일반 텍스트 비밀을 설정할 수 있습니다.

az keyvault secret set --vault-name $AZUREKEYVAULT_NAME -n DemoSecret --value MyExampleSecret

다음 섹션으로 이동하기 전에 다음 속성을 기록해 두세요.

  • Key Vault의 비밀 개체 이름
  • 개체 유형(비밀, 키 또는 인증서)
  • Key Vault 리소스의 이름
  • Key Vault가 속한 구독의 Azure 테넌트 ID

Azure Key Vault에 액세스할 ID 제공

현재 Arc 지원 클러스터의 비밀 저장소 CSI 드라이버는 서비스 주체를 통해 액세스할 수 있습니다. 아래 단계에 따라 Key Vault에 액세스할 수 있는 ID를 제공합니다.

  1. 단계에 따라 Azure에서 서비스 주체를 만듭니다. 이 단계에서 생성된 클라이언트 ID 및 클라이언트 암호를 기록해 둡니다.

  2. 다음으로 Azure Key Vault에 만든 서비스 주체에 대한 GET 권한이 있는지 확인합니다.

  3. 1단계의 클라이언트 ID 및 클라이언트 암호를 사용하여 연결된 클러스터에 Kubernetes 비밀을 만듭니다.

    kubectl create secret generic secrets-store-creds --from-literal clientid="<client-id>" --from-literal clientsecret="<client-secret>"
    
  4. 만든 비밀에 레이블을 지정합니다.

    kubectl label secret secrets-store-creds secrets-store.csi.k8s.io/used=true
    
  5. 다음 YAML을 사용하여 SecretProviderClass를 만들고 AKV 인스턴스에서 검색할 키 자격 증명 모음 이름, 테넌트 ID 및 개체에 대한 값을 채웁니다.

    # This is a SecretProviderClass example using service principal to access Keyvault
    apiVersion: secrets-store.csi.x-k8s.io/v1
    kind: SecretProviderClass
    metadata:
      name: akvprovider-demo
    spec:
      provider: azure
      parameters:
        usePodIdentity: "false"
        keyvaultName: <key-vault-name>
        cloudName:                           # Defaults to AzurePublicCloud
        objects:  |
          array:
            - |
              objectName: DemoSecret
              objectType: secret             # object types: secret, key or cert
              objectVersion: ""              # [OPTIONAL] object versions, default to latest if empty
        tenantId: <tenant-Id>                # The tenant ID of the Azure Key Vault instance
    

    국가별 클라우드와 함께 사용하려면 cloudName을 Azure Government용 AzureUSGovernmentCloud로 변경하거나 21Vianet에서 운영하는 Microsoft Azure용 AzureChinaCloud로 변경합니다.

  6. 클러스터에 SecretProviderClass를 적용합니다.

    kubectl apply -f secretproviderclass.yaml
    
  7. ID 이름을 입력하여 다음 YAML을 통해 Pod를 만듭니다.

    # This is a sample pod definition for using SecretProviderClass and service principal to access Keyvault
    kind: Pod
    apiVersion: v1
    metadata:
      name: busybox-secrets-store-inline
    spec:
      containers:
        - name: busybox
          image: k8s.gcr.io/e2e-test-images/busybox:1.29
          command:
            - "/bin/sleep"
            - "10000"
          volumeMounts:
          - name: secrets-store-inline
            mountPath: "/mnt/secrets-store"
            readOnly: true
      volumes:
        - name: secrets-store-inline
          csi:
            driver: secrets-store.csi.k8s.io
            readOnly: true
            volumeAttributes:
              secretProviderClass: "akvprovider-demo"
            nodePublishSecretRef:                       
              name: secrets-store-creds
    
  8. 클러스터에 Pod를 적용합니다.

    kubectl apply -f pod.yaml
    

비밀 유효성 검사

Pod가 시작된 후에는 배포 YAML에 지정된 볼륨 경로에 탑재된 콘텐츠를 사용할 수 있습니다.

## show secrets held in secrets-store
kubectl exec busybox-secrets-store-inline -- ls /mnt/secrets-store/

## print a test secret 'DemoSecret' held in secrets-store
kubectl exec busybox-secrets-store-inline -- cat /mnt/secrets-store/DemoSecret

추가 구성 옵션

Azure Key Vault 비밀 공급자 확장은 Helm 차트 구성을 지원합니다.

다음의 구성 설정은 Azure Key Vault 비밀 공급자 확장에 자주 사용됩니다.

구성 설정 기본값 설명
enableSecretRotation false 부울 형식입니다. true일 경우 Pod 탑재 및 Kubernetes 비밀을 외부 비밀 저장소의 최신 콘텐츠로 주기적으로 업데이트합니다.
rotationPollInterval 2분 enableSecretRotationtrue인 경우 이 설정은 비밀 회전 폴링 간격 기간을 지정합니다. 이 기간은 모든 Pod 및 Kubernetes 비밀에 대해 탑재된 콘텐츠를 최신 버전으로 다시 동기화해야 하는 빈도에 따라 조정할 수 있습니다.
syncSecret.enabled false 부울 입력입니다. 탑재된 콘텐츠를 미러링하는 Kubernetes 비밀을 만들려는 경우가 있습니다. true이면 SecretProviderClass에서 secretObjects 필드가 동기화된 Kubernetes Secret 개체의 원하는 상태를 정의하도록 허용합니다.

az k8s-extension create 명령을 사용하여 확장을 설치할 때 이러한 설정을 지정할 수 있습니다.

az k8s-extension create --cluster-name $CLUSTER_NAME --resource-group $RESOURCE_GROUP --cluster-type connectedClusters --extension-type Microsoft.AzureKeyVaultSecretsProvider --name akvsecretsprovider --configuration-settings secrets-store-csi-driver.enableSecretRotation=true secrets-store-csi-driver.rotationPollInterval=3m secrets-store-csi-driver.syncSecret.enabled=true

az k8s-extension update 명령을 사용하여 설치 후 설정을 변경할 수도 있습니다.

az k8s-extension update --cluster-name $CLUSTER_NAME --resource-group $RESOURCE_GROUP --cluster-type connectedClusters --name akvsecretsprovider --configuration-settings secrets-store-csi-driver.enableSecretRotation=true secrets-store-csi-driver.rotationPollInterval=3m secrets-store-csi-driver.syncSecret.enabled=true

배포에 필요한 경우 다른 구성 설정을 사용할 수 있습니다. 예를 들어 클러스터를 만드는 동안 kubelet 루트 디렉터리를 변경하려면 az k8s-extension create 명령을 수정합니다.

az k8s-extension create --cluster-name $CLUSTER_NAME --resource-group $RESOURCE_GROUP --cluster-type connectedClusters --extension-type Microsoft.AzureKeyVaultSecretsProvider --name akvsecretsprovider --configuration-settings linux.kubeletRootDir=/path/to/kubelet secrets-store-csi-driver.linux.kubeletRootDir=/path/to/kubelet

Azure Key Vault 비밀 공급자 확장 제거

확장을 제거하려면 다음 명령을 실행합니다.

az k8s-extension delete --cluster-type connectedClusters --cluster-name $CLUSTER_NAME --resource-group $RESOURCE_GROUP --name akvsecretsprovider

참고 항목

확장을 제거해도 확장이 설치되었을 때 생성된 CRD(사용자 지정 리소스 정의)는 삭제되지 않습니다.

확장 인스턴스가 삭제되었는지 확인하려면 다음 명령을 실행합니다.

az k8s-extension list --cluster-type connectedClusters --cluster-name $CLUSTER_NAME --resource-group $RESOURCE_GROUP

확장이 성공적으로 제거된 경우 Azure Key Vault 비밀 공급자 확장이 출력에 나열되지 않습니다. 클러스터에 다른 확장을 설치하지 않은 경우에는 빈 배열이 표시됩니다.

더 이상 필요하지 않은 경우 다음 명령을 실행하여 서비스 주체와 연결된 Kubernetes 비밀을 삭제해야 합니다.

kubectl delete secret secrets-store-creds

조정 및 문제 해결

Azure Key Vault 비밀 공급자 확장은 자체 복구됩니다. 확장이 설치되었을 때 배포된 확장 구성 요소를 누군가 변경하거나 삭제하려고 하면 해당 구성 요소가 원래 상태로 조정됩니다. CRD(사용자 지정 리소스 정의)의 경우에는 유일하게 예외가 적용됩니다. CRD가 삭제되어도 조정되지 않습니다. 삭제된 CRD를 복원하려면 기존 확장 인스턴스 이름과 함께 az k8s-extension create 명령을 다시 사용합니다.

일반적인 문제를 해결하는 방법에 대한 자세한 내용은 비밀 저장소 CSI 드라이버용 Azure Key Vault 공급자비밀 저장소 CSI 드라이버에 대한 오픈 소스 문제 해결 가이드를 참조하세요.

다음 단계