Freigeben über


Sichern Sie den eingehenden Datenverkehr mit der API-Implementierung des Gateways für Anwendungs-Routing.

Das Anwendungsrouting-Add-On unterstützt die Synchronisierung geheimer Schlüssel aus Azure Key Vault (AKV) zum Sichern des Gateway-API-Eingangsdatenverkehrs mit TLS-Beendigung. Führen Sie die folgenden Schritte aus, um Zertifikate und Schlüssel zum Beenden des TLS-Datenverkehrs am Gateway zu erstellen.

Voraussetzungen

Erforderliche Client-/Serverzertifikate und Schlüssel

  1. Erstellen Sie ein Stammzertifikat und einen privaten Schlüssel zum Signieren der Zertifikate für Beispieldienste:
mkdir httpbin_certs
openssl req -x509 -sha256 -nodes -days 365 -newkey rsa:2048 -subj '/O=example Inc./CN=example.com' -keyout httpbin_certs/example.com.key -out httpbin_certs/example.com.crt
  1. Generieren Eines Zertifikats und eines privaten Schlüssels für httpbin.example.com:
openssl req -out httpbin_certs/httpbin.example.com.csr -newkey rsa:2048 -nodes -keyout httpbin_certs/httpbin.example.com.key -subj "/CN=httpbin.example.com/O=httpbin organization"
openssl x509 -req -sha256 -days 365 -CA httpbin_certs/example.com.crt -CAkey httpbin_certs/example.com.key -set_serial 0 -in httpbin_certs/httpbin.example.com.csr -out httpbin_certs/httpbin.example.com.crt

Konfigurieren eines TLS-Eingangsgateways

Einrichten von Azure Key Vault und Synchronisieren geheimer Schlüssel mit dem Cluster

  1. Azure Key Vault erstellen

    Sie benötigen eine Azure Key Vault-Ressource , um das Zertifikat und die Schlüsseleingaben für das Anwendungsrouting-Add-On zu liefern.

    export AKV_NAME=<azure-key-vault-resource-name>  
    az keyvault create --name $AKV_NAME --resource-group $RESOURCE_GROUP --location $LOCATION
    
  2. Aktivieren Sie das Add-On Azure Key Vault-Anbieter für den Geheimnisspeicher-CSI-Treiber in Ihrem Cluster.

    az aks enable-addons --addons azure-keyvault-secrets-provider --resource-group $RESOURCE_GROUP --name $CLUSTER
    
  3. Wenn Ihr Key Vault Azure RBAC für das Berechtigungsmodell verwendet, folgen Sie den Anweisungen hier, um der vom Benutzer zugewiesenen verwalteten Identität des Add-Ons die Azure-Rolle "Key Vault Secrets User" zuzuweisen. Wenn Ihr Schlüsseltresor das Berechtigungsmodell mit Tresorzugriffsrichtlinie verwendet, können Sie alternativ die vom Benutzer zugewiesene verwaltete Identität des Add-Ons zum Zugriff auf die Azure Key Vault-Ressource unter Verwendung der Zugriffsrichtlinie autorisieren:

    OBJECT_ID=$(az aks show --resource-group $RESOURCE_GROUP --name $CLUSTER --query 'addonProfiles.azureKeyvaultSecretsProvider.identity.objectId' -o tsv | tr -d '\r')
    CLIENT_ID=$(az aks show --resource-group $RESOURCE_GROUP --name $CLUSTER --query 'addonProfiles.azureKeyvaultSecretsProvider.identity.clientId')
    TENANT_ID=$(az keyvault show --resource-group $RESOURCE_GROUP --name $AKV_NAME --query 'properties.tenantId')
    
    az keyvault set-policy --name $AKV_NAME --object-id $OBJECT_ID --secret-permissions get list
    
  4. Erstellen Sie mithilfe der Zertifikate und der Schlüssel Geheimnisse in Azure Key Vault.

    az keyvault secret set --vault-name $AKV_NAME --name test-httpbin-key --file httpbin_certs/httpbin.example.com.key
    az keyvault secret set --vault-name $AKV_NAME --name test-httpbin-crt --file httpbin_certs/httpbin.example.com.crt
    
  5. Verwenden Sie das folgende Manifest, um SecretProviderClass bereitzustellen, um für Azure Key Vault spezifische Parameter für den CSI-Treiber bereitzustellen.

    cat <<EOF | kubectl apply -f -
    apiVersion: secrets-store.csi.x-k8s.io/v1
    kind: SecretProviderClass
    metadata:
      name: httpbin-credential-spc
    spec:
      provider: azure
      secretObjects:
      - secretName: httpbin-credential
        type: kubernetes.io/tls
        data:
        - objectName: test-httpbin-key
          key: tls.key
        - objectName: test-httpbin-crt
          key: tls.crt
      parameters:
        useVMManagedIdentity: "true"
        userAssignedIdentityID: $CLIENT_ID 
        keyvaultName: $AKV_NAME
        cloudName: ""
        objects:  |
          array:
            - |
              objectName: test-httpbin-key
              objectType: secret
              objectAlias: "test-httpbin-key"
            - |
              objectName: test-httpbin-crt
              objectType: secret
              objectAlias: "test-httpbin-crt"
        tenantId: $TENANT_ID
    EOF
    

    Verwenden Sie alternativ das folgende Manifest, um direkt über Azure Key Vault auf einen Zertifikatobjekttyp zu verweisen, um SecretProviderClass bereitzustellen. In diesem Beispiel test-httpbin-cert-pfx ist der Name des Zertifikatobjekts in Azure Key Vault. Weitere Informationen finden Sie im Abschnitt zum Abrufen von Zertifikaten und Schlüsseln .

    cat <<EOF | kubectl apply -f -
    apiVersion: secrets-store.csi.x-k8s.io/v1
    kind: SecretProviderClass
    metadata:
      name: httpbin-credential-spc
    spec:
      provider: azure
      secretObjects:
      - secretName: httpbin-credential
        type: kubernetes.io/tls
        data:
        - objectName: test-httpbin-key
          key: tls.key
        - objectName: test-httpbin-crt
          key: tls.crt
      parameters:
        useVMManagedIdentity: "true"
        userAssignedIdentityID: $CLIENT_ID 
        keyvaultName: $AKV_NAME
        cloudName: ""
        objects:  |
          array:
            - |
              objectName: test-httpbin-cert-pfx  #certificate object name from keyvault
              objectType: secret
              objectAlias: "test-httpbin-key"
            - |
              objectName: test-httpbin-cert-pfx #certificate object name from keyvault
              objectType: cert
              objectAlias: "test-httpbin-crt"
        tenantId: $TENANT_ID
    EOF
    
  6. Verwenden Sie das folgende Manifest, um einen Beispielpod bereitzustellen. Der CSI-Treiber für den Geheimnisspeicher erfordert, dass ein Pod auf die SecretProviderClass-Ressource verweist, um die Synchronisierung der Geheimnisse von Azure Key Vault mit dem Cluster sicherzustellen.

    cat <<EOF | kubectl apply -f -
    apiVersion: v1
    kind: Pod
    metadata:
      name: secrets-store-sync-httpbin
    spec:
      containers:
        - name: busybox
          image: mcr.microsoft.com/oss/busybox/busybox:1.33.1
          command:
            - "/bin/sleep"
            - "10"
          volumeMounts:
          - name: secrets-store01-inline
            mountPath: "/mnt/secrets-store"
            readOnly: true
      volumes:
        - name: secrets-store01-inline
          csi:
            driver: secrets-store.csi.k8s.io
            readOnly: true
            volumeAttributes:
              secretProviderClass: "httpbin-credential-spc"
    EOF
    
    • Überprüfen Sie, ob das httpbin-credential Secret im default Namespace erstellt wurde, wie in der SecretProviderClass-Ressource definiert.

      kubectl describe secret/httpbin-credential
      

      Beispielausgabe:

      Name:         httpbin-credential
      Namespace:    default
      Labels:       secrets-store.csi.k8s.io/managed=true
      Annotations:  <none>
      
      Type:  kubernetes.io/tls
      
      Data
      ====
      tls.crt:  1180 bytes
      tls.key:  1675 bytes
      

Bereitstellen des TLS-Gateways

  1. Erstellen Sie ein Kubernetes-Gateway, das auf den httpbin-credential geheimen Schlüssel unter der TLS-Konfiguration verweist:

    cat <<EOF | kubectl apply -f -
    apiVersion: gateway.networking.k8s.io/v1
    kind: Gateway
    metadata:
      name: httpbin-gateway
    spec:
      gatewayClassName: approuting-istio
      listeners:
      - name: https
        hostname: "httpbin.example.com"
        port: 443
        protocol: HTTPS
        tls:
          mode: Terminate
          certificateRefs:
          - name: httpbin-credential
        allowedRoutes:
          namespaces:
            from: Selector
            selector:
              matchLabels:
                kubernetes.io/metadata.name: default
    EOF
    

    Erstellen Sie dann eine entsprechende HTTPRoute um die eingehenden Datenverkehrsrouten des Gateways zu konfigurieren:

    cat <<EOF | kubectl apply -f -
    apiVersion: gateway.networking.k8s.io/v1
    kind: HTTPRoute
    metadata:
      name: httpbin
    spec:
      parentRefs:
      - name: httpbin-gateway
      hostnames: ["httpbin.example.com"]
      rules:
      - matches:
        - path:
            type: PathPrefix
            value: /status
        - path:
            type: PathPrefix
            value: /delay
        backendRefs:
        - name: httpbin
          port: 8000
    EOF
    

    Rufen Sie die Gatewayadresse und den Port ab:

    kubectl wait --for=condition=programmed gateways.gateway.networking.k8s.io httpbin-gateway
    export INGRESS_HOST=$(kubectl get gateways.gateway.networking.k8s.io httpbin-gateway -o jsonpath='{.status.addresses[0].value}')
    export SECURE_INGRESS_PORT=$(kubectl get gateways.gateway.networking.k8s.io httpbin-gateway -o jsonpath='{.spec.listeners[?(@.name=="https")].port}')
    
  2. Senden Sie eine HTTPS-Anforderung für den Zugriff auf den httpbin Dienst:

    curl -v -HHost:httpbin.example.com --resolve "httpbin.example.com:$SECURE_INGRESS_PORT:$INGRESS_HOST" \
    --cacert httpbin_certs/example.com.crt "https://httpbin.example.com:$SECURE_INGRESS_PORT/status/418"
    

    Sie sollten sehen, dass der httpbin-Dienst den 418 I'm a Teapot Code zurückgibt.