AKS 구조적 인증을 사용하여 외부 ID 공급자 구성(미리 보기)

이 문서에서는 구조적 인증을 사용하여 Azure Kubernetes Service (AKS) 컨트롤 플레인 인증을 위해 GitHub 및 Google Identity 외부 ID 공급자를 구성하는 방법을 보여 줍니다. JWT(JSON Web Token) 인증자를 만들고, 클레임 유효성 검사 및 매핑을 구성하고, 인증 흐름을 테스트하는 방법을 알아봅니다.

중요합니다

AKS 미리 보기 기능은 셀프 서비스에서 사용할 수 있습니다(옵트인 방식). 미리 보기는 "있는 그대로" 및 "사용 가능한 상태로" 제공되며 서비스 수준 계약 및 제한적 보증에서 제외됩니다. AKS 미리 보기의 일부는 고객 지원팀에서 최선을 다해 지원합니다. 따라서 이러한 기능은 프로덕션 용도로 사용할 수 없습니다. 자세한 내용은 다음 지원 문서를 참조하세요.

필수 조건

  • 외부 ID 공급자를 사용하여 AKS에 인증하기 위한 개념적 개요 를 읽어보십시오.
  • Azure Cloud Shell Bash 환경을 사용합니다. 자세한 내용은 Azure Cloud Shell 시작하기를 참조하시기 바랍니다.

  • CLI 참조 명령을 로컬에서 실행하려면 Azure CLI를 설치하십시오. Windows 또는 macOS에서 실행하는 경우 Docker 컨테이너에서 Azure CLI 실행하는 것이 좋습니다. 자세한 내용은 Docker 컨테이너에서 Azure CLI 실행하는 방법 참조하세요.

    • 로컬 설치를 사용하는 경우 az login 명령을 사용하여 Azure CLI 로그인합니다. 인증 프로세스를 완료하려면 터미널에 표시되는 단계를 수행합니다. 다른 로그인 옵션은 Azure CLI 사용하여 Azure 인증을 참조하세요.

    • 메시지가 표시되면 처음 사용할 때 Azure CLI 확장을 설치합니다. 확장에 대한 자세한 내용은 Azure CLI 참조하세요.

    • az version을 실행하여 설치된 버전과 관련 종속 라이브러리를 확인합니다. 최신 버전으로 업그레이드하려면 az upgrade를 실행합니다.

  • 이 문서에는 Azure CLI 버전 2.77.0 이상이 필요합니다. Azure Cloud Shell 사용하는 경우 최신 버전이 이미 설치되어 있습니다. 로컬 컴퓨터에 Azure CLI 설치하거나 업데이트하려면 Azure CLI 참조하세요.

  • 구조적 인증 기능을 사용하려면 aks-preview Azure CLI 확장 버전 18.0.0b41 이상을 설치해야 합니다.

    • 아직 aks-preview 확장을 갖고 있지 않다면, az extension add 명령을 사용하여 이 확장을 설치하세요.

      az extension add --name aks-preview
      
    • 이미 aks-preview 확장이 있다면, 업데이트하여 이 확장이 az extension update 명령을 사용하여 최신 버전이 있는지 확인하게 하세요.

      az extension update --name aks-preview
      
    • 확인 명령 az extension show을 사용하여 확장 aks-preview의 필요한 버전이 있는지 확인하십시오.

      az extension show --name aks-preview --query version
      
  • Kubernetes 버전 1.30 이상을 실행하는 AKS 클러스터입니다. AKS 클러스터를 만들려면 Azure CLI 사용하여 Azure Kubernetes Service (AKS) 클러스터 배포를 참조하세요.

  • kubectl Kubernetes 클러스터와 상호 작용하는 명령줄 도구입니다. Azure Cloud Shell 사용하는 경우 kubectl 이미 설치되어 있습니다. kubectl을/를 로컬에 설치하려면 az aks install-cli 명령을 사용하세요.

    az aks install-cli
    
  • OIDC(OpenID Connect)를 지원하는 외부 ID 공급자입니다.

  • 클러스터 노드에서 ID 공급자로의 네트워크 연결

  • 플러그 인을 kubelogin 사용하려는 경우 kubelogin 설치 가이드의 지침에 따라 설치합니다.

환경 변수 설정

  • 리소스 그룹 및 클러스터 이름에 대해 다음 환경 변수를 설정합니다.

    export RESOURCE_GROUP="<your-resource-group-name>"
    export CLUSTER_NAME="<your-cluster-name>"
    

JWTAuthenticatorPreview 기능 등록

  1. JWTAuthenticatorPreview 기능을 az feature register 명령을 사용하여 등록합니다.

    az feature register --name JWTAuthenticatorPreview --namespace Microsoft.ContainerService
    
  2. 명령을 사용하여 기능의 등록 상태를 확인합니다 az feature show .

    az feature show --name JWTAuthenticatorPreview --namespace Microsoft.ContainerService
    
  3. 상태가 Registered로 표시되면, Microsoft.ContainerService 리소스 공급자 등록을 az provider register 명령을 사용하여 새로 고치십시오.

    az provider register --namespace Microsoft.ContainerService
    

GitHub Actions OIDC 인증 설정

  1. GitHub Actions 워크플로에 필요한 권한이 있는지 확인합니다.

  2. 워크플로 파일에서 id-token: write 사용 권한을 구성합니다. 다음은 그 예입니다.

    permissions:
      id-token: write
      contents: read
    
  3. OIDC 토큰 액세스에 적절한 리포지토리 및 조직 설정을 설정합니다. 토큰 사용에 대한 리포지토리 OIDC 설정 및 조직 보안 정책을 구성합니다.

Google Identity OAuth 2.0 인증 설정

  1. Google 클라우드 콘솔로 이동합니다.
  2. 프로젝트를 만들거나 선택합니다.
  3. OAuth 2.0 자격 증명을 만듭니다.
  4. 나중에 사용할 수 있는 클라이언트 ID 및 클라이언트 암호를 기록해 둡니다.

GitHub Actions OIDC에 대한 JWT 인증자 구성 만들기

  • 다음 구성으로 명명된 jwt-config.json 파일을 만듭니다.

    {
      "issuer": {
          "url": "https://token.actions.githubusercontent.com",
          "audiences": [
              "my-api"
          ]
      },
      "claimValidationRules": [
          {
              "expression": "has(claims.sub)",
              "message": "must have sub claim"
          }
      ],
      "claimMappings": {
          "username": {
              "expression": "'aks:jwt:github:' + claims.sub"
          }
      },
      "userValidationRules": [
          {
              "expression": "has(user.username)",
              "message": "must have username"
          },
          {
              "expression": "!user.username.startsWith('aks:jwt:github:system')",
              "message": "username must not start with 'aks:jwt:github:system'"
          }
      ]
    }
    

Google ID에 대한 JWT 인증자 구성 만들기

  • 다음 구성으로 명명된 jwt-config.json 파일을 만듭니다.

    {
        "issuer": {
            "url": "https://accounts.google.com",
            "audiences": [
                "your-client-id.apps.googleusercontent.com"
            ]
        },
        "claimValidationRules": [
            {
                "expression": "has(claims.sub)",
                "message": "must have sub claim"
            }
        ],
        "claimMappings": {
            "username": {
                "expression": "'aks:jwt:google:' + claims.sub"
            },
            "groups": {
                "expression": "has(claims.groups) ? claims.groups.split(',').map(g, 'aks:jwt:' + g) : []"
            }
        },
        "userValidationRules": [
            {
                "expression": "has(user.username)",
                "message": "must have username"
            },
            {
                "expression": "!user.username.startsWith('aks:jwt:google:system')",
                "message": "username must not start with 'aks:jwt:google:system'"
            }
        ]
    }
    

JWT 인증자 구성 요소

JWT 인증자 구성에는 다음과 같은 주요 요소가 issuerclaimValidationRulesclaimMappingsuserValidationRules포함됩니다. 각 요소는 AKS가 외부 ID 공급자에서 JWT 토큰의 유효성을 검사하고 처리하는 방법을 정의하는 특정 용도로 사용됩니다.

발급자 구성

issuer 구성의 주요 요소에 대해 다음 표에서는 설명합니다.

발급자 구성 요소 설명
url JWT의 iss 클레임과 일치해야 하는 OIDC 발급자 URL입니다.
audiences JWT가 발급될 대상으로 지정된 그룹의 목록입니다(aud 클레임에 대해 확인됨).

클레임 유효성 검사 규칙 구성

claimValidationRules 구성의 주요 요소에 대해 다음 표에서는 설명합니다.

클레임 유효성 검사 규칙 요소 설명
expression JWT 클레임에 적용할 유효성 검사 논리를 정의하는 CEL 식입니다. 토큰이 허용되려면 표현식이 true로 평가되어야 합니다.
message 유효성 검사 규칙이 실패하면 오류 메시지가 반환됩니다.

클레임 매핑 구성

claimMappings 구성의 주요 요소에 대해 다음 표에서는 설명합니다.

클레임 매핑 요소 설명
username JWT 클레임에서 Kubernetes 사용자 이름을 생성하는 방법을 정의하는 CEL 식입니다. 다른 인증 방법과의 aks:jwt: 충돌을 방지하려면 접두사를 포함해야 합니다.
groups JWT 클레임에서 Kubernetes 그룹 멤버 자격을 생성하는 방법을 정의하는 CEL 식입니다. 다른 인증 방법과의 aks:jwt: 충돌을 방지하려면 접두사를 포함해야 합니다.
uid 사용자에 대한 고유 식별자를 정의하는 선택적 CEL 식입니다.
extra CEL 식으로 정의된 추가 사용자 특성의 선택적 맵입니다.

사용자 유효성 검사 규칙 구성

userValidationRules 구성의 주요 요소에 대해 다음 표에서는 설명합니다.

사용자 유효성 검사 규칙 요소 설명
expression 최종 매핑된 사용자 정보에 적용할 추가 유효성 검사 논리를 정의하는 CEL 식입니다. 사용자가 수락되려면 식이 true로 평가되어야 합니다.
message 사용자 유효성 검사 규칙이 실패하면 오류 메시지가 반환됩니다.

JWT 인증자 만들기

  • 명령을 사용하여 AKS 클러스터에 JWT 인증자를 추가합니다 az aks jwtauthenticator add .

    az aks jwtauthenticator add \
        --resource-group $RESOURCE_GROUP \
        --cluster-name $CLUSTER_NAME \
        --name external-auth \
        --config-file jwt-config.json
    

JWT 인증자 관리

모든 JWT 인증자 나열

  • 명령을 사용하여 클러스터의 모든 JWT 인증자를 나열합니다 az aks jwtauthenticator list .

    az aks jwtauthenticator list \
        --resource-group $RESOURCE_GROUP \
        --cluster-name $CLUSTER_NAME
    

특정 JWT 인증자에 대한 세부 정보 가져오기

  • 명령을 사용하여 az aks jwtauthenticator show 특정 JWT 인증자에 대한 세부 정보를 가져옵니다.

    az aks jwtauthenticator show \
        --resource-group $RESOURCE_GROUP \
        --cluster-name $CLUSTER_NAME \
        --name external-auth
    

인증을 위해 GitHub Actions OIDC 설정

  1. 환경 변수를 만들고 GitHub 리포지토리에서 다음과 같은 필수 리포지토리 비밀을 설정합니다.

    • AKS_SERVER_URL: AKS 클러스터의 API 서버 URL입니다.
    • AKS_CA_DATA: AKS 클러스터에 대한 Base64로 인코딩된 인증 기관 데이터입니다.
  2. OIDC 토큰을 가져와 AKS 클러스터로 인증하는 데 사용하는 워크플로를 만듭니다. 다음 예제 워크플로는 클러스터에서 실행되는 모든 Pod를 가져옵니다.

    비고

    대상 그룹 값 my-apiJWT 인증자 구성에 구성된 대상과 일치해야 합니다.

    name: AKS Access with GitHub OIDC
    on:
      workflow_dispatch:
      push:
        branches: [main]
    
    permissions:
      id-token: write
      contents: read
    
    jobs:
      aks-access:
        runs-on: ubuntu-latest
        steps:
          - name: Checkout code
            uses: actions/checkout@v4
    
          - name: Install kubectl
            uses: azure/setup-kubectl@v3
            with:
              version: 'latest'
    
          - name: Get GitHub OIDC token
            id: get_token
            run: |
              TOKEN=$(curl -H "Authorization: Bearer $ACTIONS_ID_TOKEN_REQUEST_TOKEN" \
                "$ACTIONS_ID_TOKEN_REQUEST_URL&audience=my-api" | \
                jq -r '.value')
              echo "::add-mask::$TOKEN"
              echo "oidc_token=$TOKEN" >> $GITHUB_OUTPUT
    
          - name: Create kubeconfig with OIDC token
            run: |
              cat <<EOF > kubeconfig
              apiVersion: v1
              kind: Config
              clusters:
              - cluster:
                  certificate-authority-data: ${{ secrets.AKS_CA_DATA }}
                  server: ${{ secrets.AKS_SERVER_URL }}
                name: aks-cluster
              contexts:
              - context:
                  cluster: aks-cluster
                  user: github-oidc-user
                name: aks-context
              current-context: aks-context
              users:
              - name: github-oidc-user
                user:
                  token: ${{ steps.get_token.outputs.oidc_token }}
              EOF
    
          - name: List all pods in the cluster
            run: |
              export KUBECONFIG=./kubeconfig
              kubectl get pods --all-namespaces
    

JWT 인증자 구성에 대한 클러스터 정보 가져오기

  1. 명령을 사용하여 클러스터에 대한 API 서버 URL을 가져옵니다 az aks show .

    az aks show --resource-group $RESOURCE_GROUP --name $CLUSTER_NAME --query "fqdn" -o tsv | \
      awk '{print "https://" $0 ":443"}'
    
  2. 명령을 사용하여 az aks get-credentials 클러스터에 대한 base64로 인코딩된 인증 기관 데이터를 가져옵니다.

    # Get CA data (base64 encoded)
    az aks get-credentials --resource-group $RESOURCE_GROUP --name $CLUSTER_NAME --file - --format exec | \
      grep certificate-authority-data | awk '{print $2}'
    

인증을 위해 Google Identity OAuth 2.0 설정

플러그 인을 사용하거나 정적 토큰을 kubelogin 직접 사용하여 Google ID 인증을 설정할 수 있습니다.

  • kubeconfig 파일에 새 사용자 컨텍스트를 추가합니다. 다음은 그 예입니다.

    users:
    - name: external-user
      user:
        exec:
          apiVersion: client.authentication.k8s.io/v1beta1
          command: kubectl
          args:
          - oidc-login
          - get-token
          - --oidc-issuer-url=https://accounts.google.com
          - --oidc-client-id=your-client-id.apps.googleusercontent.com
          - --oidc-client-secret=your-client-secret
    

인증 테스트

  1. 메인 브랜치로 푸시하거나 리포지토리의 Actions 탭에서 수동으로 트리거하여 워크플로를 트리거합니다.

  2. 작업 탭에서 워크플로 실행을 모니터링하여 인증이 작동하는지 확인합니다.

    RBAC(Role-Based Access Control) 구성 전에 처음 설치할 예상 출력:

    Error from server (Forbidden): nodes is forbidden: User "aks:jwt:github:your-sub" cannot list resource "nodes" in API group "" at the cluster scope
    

    이 오류는 인증에 성공했지만 권한 부여가 없음을 나타냅니다.

  • kubectl get nodes 명령의 --user 플래그를 사용하여 Google ID 인증을 위해 만든 사용자 컨텍스트를 지정하고 인증을 테스트합니다. 다음은 그 예입니다.

    kubectl get nodes --user external-user
    

    RBAC(Role-Based Access Control) 구성 전에 처음 설치할 예상 출력:

    Error from server (Forbidden): nodes is forbidden: User "aks:jwt:google:your-subject" cannot list resource "nodes" in API group "" at the cluster scope
    

    이 오류는 인증에 성공했지만 권한 부여가 없음을 나타냅니다.

Kubernetes 역할 기반 접근 제어(RBAC) 구성

외부 사용자에 대한 적절한 RBAC 바인딩을 만들고 클러스터 관리자 자격 증명을 사용하여 이러한 구성을 적용합니다.

  1. 외부 사용자에 대한 RBAC 바인딩을 구성하기 위해 명명된 rbac-config.yaml 파일을 만듭니다. 다음은 그 예입니다.

    apiVersion: rbac.authorization.k8s.io/v1
    kind: ClusterRole
    metadata:
      name: external-user-role
    rules:
    - apiGroups: [""]
      resources: ["pods", "services", "nodes"]
      verbs: ["get", "list"]
    - apiGroups: ["apps"]
      resources: ["deployments", "replicasets"]
      verbs: ["get", "list"]
    ---
    apiVersion: rbac.authorization.k8s.io/v1
    kind: ClusterRoleBinding
    metadata:
      name: external-user-binding
    subjects:
    - kind: User
      # This matches the username expression in claim mappings for GitHub; example of GitHub subject is "repo:<organization-name>/<repository-name>:ref:refs/heads/main"
      name: aks:jwt:github:your-github-sub
      apiGroup: rbac.authorization.k8s.io
    roleRef:
      kind: ClusterRole
      name: external-user-role
      apiGroup: rbac.authorization.k8s.io
    
  2. 다음 명령을 사용하여 RBAC 구성을 적용합니다.kubectl apply

    kubectl apply -f rbac-config.yaml
    
  1. 외부 사용자에 대한 RBAC 바인딩을 구성하기 위해 명명된 rbac-config.yaml 파일을 만듭니다. 다음은 그 예입니다.

    apiVersion: rbac.authorization.k8s.io/v1
    kind: ClusterRole
    metadata:
      name: external-user-role
    rules:
    - apiGroups: [""]
      resources: ["pods", "services", "nodes"]
      verbs: ["get", "list"]
    - apiGroups: ["apps"]
      resources: ["deployments", "replicasets"]
      verbs: ["get", "list"]
    ---
    apiVersion: rbac.authorization.k8s.io/v1
    kind: ClusterRoleBinding
    metadata:
      name: external-user-binding
    subjects:
    - kind: User
      # This matches the username expression in claim mappings for Google
      name: aks:jwt:google:your-subject-claim
      apiGroup: rbac.authorization.k8s.io
    roleRef:
      kind: ClusterRole
      name: external-user-role
      apiGroup: rbac.authorization.k8s.io
    
  2. 다음 명령을 사용하여 RBAC 구성을 적용합니다.kubectl apply

    kubectl apply -f rbac-config.yaml
    

RBAC를 사용하여 액세스 확인

  • 외부 사용자가 kubectl get nodeskubectl get pods 명령과 함께 --user 플래그를 사용하여 구성한 RBAC 권한에 따라 이제 리소스에 액세스할 수 있는지 확인합니다. 다음은 그 예입니다.

    kubectl get nodes --user external-user
    kubectl get pods --user external-user
    

JWT 인증자 제거

  • JWT 인증자가 더 이상 필요하지 않은 경우 명령을 사용하여 az aks jwtauthenticator delete AKS 클러스터에서 제거합니다.

    az aks jwtauthenticator delete \
        --resource-group $RESOURCE_GROUP \
        --cluster-name $CLUSTER_NAME \
        --name external-auth