Sicherheitsgruppen für pods - Amazon EKS

Sicherheitsgruppen für pods

Sicherheitsgruppen für pods integrieren Amazon-EC2-Sicherheitsgruppen in Kubernetespods. Sie können Amazon-EC2-Sicherheitsgruppen verwenden, um Regeln zu definieren, die ein- und ausgehenden Netzwerkverkehr zu und von pods zulassen, die Sie auf Knoten bereitstellen, die auf vielen Amazon-EC2-Instance-Typen und Fargate ausgeführt werden. Eine ausführliche Erläuterung dieser Funktion finden Sie im Blogbeitrag Einführung in Sicherheitsgruppen für pods.

Überlegungen

Berücksichtigen Sie vor der Bereitstellung von Sicherheitsgruppen für pods die folgenden Beschränkungen und Bedingungen:

  • Pods, die auf Amazon-EC2-Knoten ausgeführt werden, können sich in jeder von Amazon EKS unterstützten Kubernetes-Version befinden, aber pods, die auf Fargate ausgeführt werden, müssen sich in einem Cluster der Version 1.18 oder höher befinden.

  • Sicherheitsgruppen für pods können nicht mit Windows-Knoten verwendet werden.

  • Sicherheitsgruppen für pods können nicht mit Clustern verwendet werden, die für die IPv6-Familie konfiguriert sind, die Amazon-EC2-Knoten enthalten. Sie können Sicherheitsgruppen jedoch für pods mit Clustern verwenden, die für die IPv6-Familie konfiguriert sind, die nur Fargate-Knoten enthalten. Weitere Informationen finden Sie unter Zuweisen von IPv6-Adressen zu pods und services.

  • Sicherheitsgruppen für pods werden von den meisten Nitro-basierten Familien von Amazon-EC2-Instances unterstützt, einschließlich der Instance-Familien m5, c5, r5, p3, m6g, c6g und r6g. Die t3-Instance-Familie wird nicht unterstützt. Eine vollständige Liste der unterstützten Instances finden Sie in der Datei limits.go auf GitHub. Ihre Knoten müssen von einem der aufgelisteten Instance-Typen sein, die in der Datei mit IsTrunkingCompatible: true gekennzeichnet sind.

  • Wenn Sie auch pod-Sicherheitsrichtlinien verwenden, um den Zugriff auf die pod-Mutation einzuschränken, müssen die eks-vpc-resource-controller-Servicekonten vpc-resource-controller und Kubernetes in Kubernetes-ClusterRoleBinding für das role angegeben werden, dem Ihr psp zugewiesen ist. Wenn Sie die standardmäßigen Amazon-EKS-psp, -role, und -ClusterRoleBinding verwenden, ist dies die eks:podsecuritypolicy:authenticated ClusterRoleBinding. Sie würden beispielsweise die Servicekonten zum Abschnitt subjects: hinzufügen, wie im folgenden Beispiel gezeigt:

    ... subjects: - kind: Group apiGroup: rbac.authorization.k8s.io name: system:authenticated - kind: ServiceAccount name: vpc-resource-controller - kind: ServiceAccount name: eks-vpc-resource-controller
  • Wenn Sie benutzerdefinierte Netzwerk- und Sicherheitsgruppen für pods zusammen verwenden, wird die durch Sicherheitsgruppen für pods angegebene Sicherheitsgruppe anstelle der im ENIconfig angegebenen Sicherheitsgruppe verwendet.

  • Wenn Sie Version 1.10.2 oder älter des Amazon-VPC-CNI-Plugins verwenden und die Einstellung terminationGracePeriodSeconds in Ihre pod-Spezifikation aufnehmen, darf der Wert der Einstellung nicht Null sein.

  • Wenn Sie Version 1.10 oder neuer des Amazon-VPC-CNI-Plugins verwenden oder Version 1.11 mit POD_SECURITY_GROUP_ENFORCING_MODE=strict, was die Standardeinstellung ist, dann werden Kubernetes-Services vom Typ NodePort und LoadBalancer, die Instance-Ziele verwenden, für die externalTrafficPolicy auf Local eingestellt ist, nicht für pods unterstützt, denen Sie Sicherheitsgruppen zuweisen. Weitere Informationen zur Verwendung eines Load Balancers mit Instance-Zielen finden Sie unter Netzwerklastenausgleich auf Amazon EKS. Wenn Sie Version 1.11 des Plugins oder höher mit POD_SECURITY_GROUP_ENFORCING_MODE=standard verwenden, dann werden Instance-Ziele mit der Einstellung Local für externalTrafficPolicy unterstützt.

  • Wenn Sie Version 1.10 des Amazon-VPC-CNI-Plugins oder höher verwenden oder Version 1.11 mit POD_SECURITY_GROUP_ENFORCING_MODE=strict, was die Standardeinstellung ist, ist die Quell-NAT für von pods mit zugewiesenen Sicherheitsgruppen ausgehenden Datenverkehr deaktiviert, damit Sicherheitsgruppenregeln für ausgehenden Datenverkehr angewendet werden können. Um auf das Internet zuzugreifen, müssen pods mit zugewiesenen Sicherheitsgruppen auf Knoten gestartet werden, die in einem privaten Subnetz bereitgestellt werden, das mit einem NAT-Gateway oder einer NAT-Instance konfiguriert ist. Pods mit zugewiesenen Sicherheitsgruppen, die in öffentlichen Subnetzen bereitgestellt werden, haben keinen Internetzugriff.

    Wenn Sie Version 1.11 oder höher des Plugins mit POD_SECURITY_GROUP_ENFORCING_MODE=standard verwenden, wird pod-Datenverkehr, der für außerhalb der VPC bestimmt ist, an die IP-Adresse der primären Netzwerkschnittstelle der Instance weitergeleitet. Für diesen Datenverkehr werden die Regeln in den Sicherheitsgruppen für die primäre Netzwerkschnittstelle anstelle der Regeln in den pod's-Sicherheitsgruppen verwendet.

  • Um die Calico-Netzwerkrichtlinie mit pods zu verwenden, denen Sicherheitsgruppen zugewiesen sind, müssen Sie Version 1.11.0 oder höher des Amazon-VPC-CNI-Plugins verwenden und POD_SECURITY_GROUP_ENFORCING_MODE=standard festlegen. Andernfalls wird Datenverkehr zu und von pods mit zugehörigen Sicherheitsgruppen nicht von den Calico-Netzwerkrichtlinien geregelt, sondern es gelten ausschließlich die Amazon-EC2-Sicherheitsgruppen. Informationen zum Aktualisieren Ihrer Version von Amazon VPC CNI finden Sie unter Verwalten der Amazon VPC CNI plugin for Kubernetes.

  • Pods, die auf Amazon EC2-Knoten ausgeführt werden, die Sicherheitsgruppen in Clustern verwenden, die Nodelocal DNSCache verwenden, werden nur mit Version 1.11.0 oder höher des Amazon-VPC-CNI-Plugins mit der Einstellung POD_SECURITY_GROUP_ENFORCING_MODE=standard unterstützt. Informationen zum Aktualisieren Ihrer Version des Amazon-VPC-CNI-Plugins finden Sie unter Verwalten der Amazon VPC CNI plugin for Kubernetes.

Das Amazon-VPC-CNI-Add-on für Sicherheitsgruppen für pods konfigurieren

Sicherheitsgruppen für pods bereitstellen

Wenn Sie Sicherheitsgruppen nur für Fargate-pods verwenden und keine Amazon-EC2-Knoten in Ihrem Cluster haben, fahren Sie mit Schritt Eine Beispielanwendung bereitstellen fort.

  1. Überprüfen Sie Ihre aktuelle CNI-Plugin-Version mit dem folgenden Befehl:

    kubectl describe daemonset aws-node --namespace kube-system | grep Image | cut -d "/" -f 2

    Die Beispielausgabe lautet wie folgt.

    amazon-k8s-cni-init:1.7.5-eksbuild.1 amazon-k8s-cni:1.7.5-eksbuild.1

    Wenn Ihre CNI-Plugin-Version älter als 1.7.7 ist, aktualisieren Sie Ihr CNI-Plugin auf Version 1.7.7 oder höher. Weitere Informationen finden Sie unter Aktualisieren des Amazon VPC CNI plugin for Kubernetes-Add-ons.

  2. Fügen Sie die verwaltete AmazonEKSVPCResourceController-Richtlinie der Cluster-Rolle hinzu, die Ihrem Amazon-EKS-Cluster zugeordnet ist. Die Richtlinie ermöglicht es der Rolle, Netzwerkschnittstellen, ihre privaten IP-Adressen sowie deren An- und Abkopplung an und von Netzwerk-Instances zu verwalten.

    1. Bestimmen Sie den ARN Ihrer Cluster-IAM-Rolle. Ersetzen Sie my-cluster mit dem Namen Ihres Clusters.

      aws eks describe-cluster --name my-cluster --query cluster.roleArn --output text

      Die Beispielausgabe lautet wie folgt.

      arn:aws:iam::111122223333:role/eksClusterRole
    2. Der folgende Befehl fügt die Richtlinie einer Cluster-Rolle namens eksClusterRole hinzu. Ersetzen Sie eksClusterRole durch den Namen Ihrer Rolle.

      aws iam attach-role-policy \ --policy-arn arn:aws:iam::aws:policy/AmazonEKSVPCResourceController \ --role-name eksClusterRole
  3. Aktivieren Sie das Amazon-VPC-CNI-Add-on, um Netzwerkschnittstellen für pods zu verwalten, indem Sie die ENABLE_POD_ENI-Variable im aws-node DaemonSet auf true setzen. Sobald diese Einstellung auf true gesetzt ist, fügt das Add-on für jeden Knoten im Cluster eine Markierung mit dem Wert vpc.amazonaws.com/has-trunk-attached=true hinzu. Der VPC-Ressourcen-Controller erstellt und verknüpft eine spezielle Netzwerkschnittstelle, die als Trunk-Netzwerkschnittstelle mit der Beschreibung aws-k8s-trunk-eni bezeichnet wird.

    kubectl set env daemonset aws-node -n kube-system ENABLE_POD_ENI=true
    Anmerkung

    Die Trunk-Netzwerkschnittstelle ist in der maximalen Anzahl von Netzwerkschnittstellen enthalten, die vom Instance-Typ unterstützt werden. Eine Liste der maximalen Anzahl von Netzwerkschnittstellen, die von jedem Instance-Typ unterstützt werden, finden Sie unter IP-Adressen pro Netzwerkschnittstelle pro Instance-Typ im Amazon-EC2-Benutzerhandbuch für Linux-Instances. Wenn an Ihren Knoten bereits die maximale Anzahl an Standardnetzwerkschnittstellen angeschlossen ist, reserviert der VPC-Ressourcencontroller einen Speicherplatz. Sie müssen Ihre laufenden pods so weit herunterskalieren, dass der Controller eine Standard-Netzwerkschnittstelle trennen und löschen, die Trunk-Netzwerkschnittstelle erstellen und an die Instance anhängen kann.

    Mit dem folgenden Befehl können Sie sehen, bei welchen Ihrer Knoten aws-k8s-trunk-eni auf true gesetzt ist. Wenn No resources found zurückgegeben wird, warten Sie einige Sekunden und versuchen Sie es dann erneut. Der vorherige Schritt erfordert einen Neustart des CNI-pods, was mehrere Sekunden dauert.

    kubectl get nodes -o wide -l vpc.amazonaws.com/has-trunk-attached=true

    Nachdem die Trunk-Netzwerkschnittstelle erstellt wurde, werden pods sekundäre IP-Adressen von der Trunk- oder Standardnetzwerkschnittstelle zugewiesen. Die Trunk-Schnittstelle wird automatisch gelöscht, wenn der Knoten gelöscht wird.

    Wenn Sie in einem späteren Schritt eine Sicherheitsgruppe für einen pod bereitstellen, erstellt der VPC-Ressourcen-Controller eine spezielle Netzwerkschnittstelle, die als Zweigstellennetzwerkschnittstelle bezeichnet wird, mit einer Beschreibung von aws-k8s-branch-eni und ordnet ihr die Sicherheitsgruppen zu. Neben den an den Knoten angeschlossenen Standard- und Amtsnetzschnittstellen werden Nebenstellennetzschnittstellen erstellt. Wenn Sie Lebend- oder Bereitschaftserkennung verwenden, müssen Sie auch das frühe TCP-Demux deaktivieren, damit das kubelet über TCP eine Verbindung zu pods auf Zweigstellennetzwerkschnittstellen herstellen kann. Führen Sie den folgenden Befehl aus, um das frühe TCP-Demux zu deaktivieren:

    kubectl patch daemonset aws-node \ -n kube-system \ -p '{"spec": {"template": {"spec": {"initContainers": [{"env":[{"name":"DISABLE_TCP_EARLY_DEMUX","value":"true"}],"name":"aws-vpc-cni-init"}]}}}}'
    Anmerkung

    Wenn Sie 1.11.0 oder höher des Amazon VPC CNI plugin for Kubernetes-Add-ons verwenden und POD_SECURITY_GROUP_ENFORCING_MODE=standard gilt, wie im nächsten Schritt beschrieben, müssen Sie den vorherigen Befehl nicht ausführen.

  4. Wenn Ihr Cluster NodeLocal DNSCache verwendet oder Sie auf pods, die eigene Sicherheitsgruppen haben, die Calico-Netzwerkrichtlinie anwenden möchten, oder wenn Sie für pods, denen Sie Sicherheitsgruppen zuweisen möchten, Kubernetes-Services vom Typ NodePort und LoadBalancer haben, die Instance-Ziele mit einer externalTrafficPolicy auf Local verwenden, dann müssen Sie Version 1.11.0 oder höher des Amazon VPC CNI plugin for Kubernetes-Add-ons verwenden, und Sie müssen die folgende Einstellung aktivieren:

    kubectl set env daemonset aws-node -n kube-system POD_SECURITY_GROUP_ENFORCING_MODE=standard
    Wichtig
    • Pod-Sicherheitsgruppenregeln werden nicht auf den Datenverkehr zwischen pods oder zwischen pods und services, wie beispielsweise kubelet oder nodeLocalDNS, angewendet, die sich auf demselben Knoten befinden.

    • Für ausgehenden Datenverkehr von pods an Adressen außerhalb der VPC wird die Netzwerkadresse in die IP-Adresse der primären Netzwerkschnittstelle der Instance übersetzt (es sei denn, Sie haben auch AWS_VPC_K8S_CNI_EXTERNALSNAT=true festgelegt). Für diesen Datenverkehr werden die Regeln in den Sicherheitsgruppen für die primäre Netzwerkschnittstelle anstelle der Regeln in den pod's-Sicherheitsgruppen verwendet.

    • Damit diese Einstellung auf vorhandene pods angewendet wird, müssen Sie die pods oder die Knoten, auf denen die pods ausgeführt werden, neu starten.

  5. Erstellen Sie einen Namespace zum Bereitstellen von Ressourcen.

    kubectl create namespace my-namespace
  6. Stellen Sie ein Amazon EKS SecurityGroupPolicy in Ihrem Cluster bereit.

    1. Speichern Sie die folgende Beispielsicherheitsrichtlinie in einer Datei mit dem Namen my-security-group-policy.yaml. Sie können podSelector durch serviceAccountSelector ersetzen, wenn Sie pods lieber basierend auf Servicekontomarkierungen auswählen möchten. Sie müssen den einen oder anderen Selektor angeben. Ein leeres podSelector (Beispiel: podSelector: {}) wählt alle pods im Namespace aus. Ein leeres serviceAccountSelector wählt alle Servicekonten im Namespace aus. Sie müssen 1-5 Sicherheitsgruppen-IDs für groupIds angeben. Falls Sie mehr als eine ID angeben, gilt die Kombination aller Regeln in allen Sicherheitsgruppen für die ausgewählten pods.

      apiVersion: vpcresources.k8s.aws/v1beta1 kind: SecurityGroupPolicy metadata: name: my-security-group-policy namespace: my-namespace spec: podSelector: matchLabels: role: my-role securityGroups: groupIds: - sg-abc123
      Wichtig
      • Die Sicherheitsgruppen, welche Sie in der Richtlinie angeben, müssen vorhanden sein. Wenn sie nicht vorhanden sind, bleibt Ihr pod im Erstellungsprozess hängen, wenn Sie einen pod bereitstellen, der dem Selektor entspricht. Wenn Sie den pod beschreiben, wird eine Fehlermeldung ähnlich der folgenden angezeigt: An error occurred (InvalidSecurityGroupID.NotFound) when calling the CreateNetworkInterface operation: The securityGroup ID 'sg-abc123' does not exist.

      • Die Sicherheitsgruppe muss eingehende Kommunikation von der Cluster-Sicherheitsgruppe (für kubelet) über alle Ports zulassen, für die Sie Probes konfiguriert haben.

      • Die Sicherheitsgruppe muss ausgehende Kommunikation mit einer Sicherheitsgruppe zulassen, die eingehenden TCP- und UDP-Port 53 (für CoreDNS-pods) von ihr zulässt.

      • Wenn Sie die Sicherheitsgruppen-Richtlinie mit Fargate verwenden, stellen Sie sicher, dass Ihre Sicherheitsgruppe über Regeln verfügt, die es den pods ermöglichen, mit der Kubernetes-Steuerebene zu kommunizieren. Am einfachsten erreichen Sie dies, indem Sie die Cluster-Sicherheitsgruppe als eine der Sicherheitsgruppen angeben.

      • Sicherheitsgruppenrichtlinien gelten nur für neu geplante pods. Sie haben keinen Einfluss auf laufende pods.

    2. Die Richtlinie bereitstellen.

      kubectl apply -f my-security-group-policy.yaml
  7. Stellen Sie eine Beispielanwendung mit einem Label bereit, das dem my-role-Wert für podselector entspricht, den Sie im vorherigen Schritt angegeben haben.

    1. Speichern Sie den folgenden Inhalt in einer Datei.

      apiVersion: apps/v1 kind: Deployment metadata: name: my-deployment namespace: my-namespace labels: app: my-app spec: replicas: 1 selector: matchLabels: app: my-app template: metadata: labels: app: my-app role: my-role spec: containers: - name: my-container image: my-image ports: - containerPort: 80
    2. Stellen Sie die Anwendung mit dem folgenden Befehl bereit. Wenn Sie die Anwendung bereitstellen, entspricht das Amazon VPC CNI plugin for Kubernetes der role-Markierung und die Sicherheitsgruppen, die Sie im vorherigen Schritt angegeben haben, werden auf den pod angewendet.

      kubectl apply -f my-security-group-policy.yaml
      Anmerkung
      • Wenn Ihr pod im Waiting-Zustand hängen bleibt und Sie Insufficient permissions: Unable to create Elastic Network Interface. sehen, wenn Sie den pod beschreiben, bestätigen Sie, dass Sie die IAM-Richtlinie in einem vorherigen Schritt zur IAM-Cluster-Rolle hinzugefügt haben.

      • Wenn Ihr pod im Status Pending feststeckt, überprüfen Sie, ob für Ihren Knoten-Instance-Typ IsTrunkingCompatible: true in limits.go auf GitHub festgelegt ist, und dass die maximale Anzahl der vom Instance-Typ unterstützten Zweigstellennetzwerkschnittstellen multipliziert mit der Anzahl der Knoten in Ihrer Knotengruppe noch nicht erreicht wurde. Eine m5.large-Instance unterstützt beispielsweise neun Zweigstellen-Netzwerkschnittstellen. Wenn Ihre Knotengruppe fünf Knoten hat, können maximal 45 Zweigstellen-Netzwerkschnittstellen für die Knotengruppe erstellt werden. Der 46. pod, den Sie bereitstellen möchten, bleibt im Pending-Zustand, bis ein anderer pod mit zugehörigen Sicherheitsgruppen gelöscht wird.

      Wenn Sie kubectl describe pod my-deployment-xxxxxxxxxx-xxxxx -n my-namespace ausführen und eine Meldung ähnlich der folgenden Meldung angezeigt wird, kann sie problemlos ignoriert werden. Diese Meldung kann erscheinen, wenn das CNI-Plug-In versucht, das Host-Netzwerk einzurichten, und dies fehlschlägt, während die Netzwerkschnittstelle erstellt wird. Das Amazon VPC CNI plugin for Kubernetes protokolliert dieses Ereignis, bis die Netzwerkschnittstelle erstellt wird.

      Failed to create pod sandbox: rpc error: code = Unknown desc = failed to set up sandbox container "e24268322e55c8185721f52df6493684f6c2c3bf4fd59c9c121fd4cdc894579f" network for pod "my-deployment-59f5f68b58-c89wx": networkPlugin cni failed to set up pod "my-deployment-59f5f68b58-c89wx_my-namespace" network: add cmd: failed to assign an IP address to container

      Die maximale Anzahl von pods, die auf dem Instance-Typ ausgeführt werden können, darf nicht überschritten werden. Eine Liste der maximalen Anzahl von pods, die Sie auf jedem Instance-Typ ausführen können, finden Sie unter eni-max-pods.txt auf GitHub. Wenn Sie einen pod mit zugeordneten Sicherheitsgruppen oder den Knoten löschen, auf dem der pod ausgeführt wird, löscht der VPC-Ressourcen-Controller die Zweigstellennetzwerkschnittstelle. Wenn Sie einen Cluster mit pods löschen, die pods für Sicherheitsgruppen verwenden, löscht der Controller die Zweigstellennetzwerkschnittstellen nicht, sodass Sie sie selbst löschen müssen.

Eine Beispielanwendung bereitstellen

Um Sicherheitsgruppen für pods zu verwenden, müssen Sie über eine bestehende Sicherheitsgruppe verfügen und auf Ihrem Cluster die Amazon-EKS-SecurityGroupPolicy bereitstellen, wie nachfolgend beschrieben. In den folgenden Schritten wird gezeigt, wie Sie die Sicherheitsgruppenrichtlinie für ein pod verwenden. Wenn nicht anders angegeben, führen Sie alle Schritte vom selben Terminal aus, da Variablen in den folgenden Schritten verwendet werden, die nicht über Terminals hinweg bestehen bleiben.

Ein Beispiel-pod mit einer Sicherheitsgruppe bereitstellen

  1. Erstellen Sie eine Sicherheitsgruppe zur Verwendung mit Ihrem pod Die folgenden Schritte zeigen, wie Sie eine einfache Sicherheitsgruppe erstellen. In einem Produktionscluster werden Sie wahrscheinlich andere Regeln verwenden.

    1. Rufen Sie die IDs der VPC- und Cluster-Sicherheitsgruppe Ihres Clusters ab. Ersetzen Sie my-cluster mit dem Namen Ihres Clusters.

      my_cluster_name=my-cluster my_cluster_vpc_id=$(aws eks describe-cluster \ --name $my_cluster_name \ --query cluster.resourcesVpcConfig.vpcId \ --output text) my_cluster_security_group_id=$(aws eks describe-cluster \ --name $my_cluster_name \ --query cluster.resourcesVpcConfig.clusterSecurityGroupId \ --output text)
    2. Erstellen Sie die Sicherheitsgruppe für Ihren pod. Ersetzen Sie my-pod-security-group durch Ihr eigenes. Notieren Sie sich die ID der Sicherheitsgruppe, die nach dem Ausführen der Befehle in der Ausgabe zurückgegeben wurde. Sie werden sie in einem späteren Schritt noch benötigen.

      my_pod_security_group_name=my-pod-security-group aws ec2 create-security-group \ --vpc-id $my_cluster_vpc_id \ --group-name $my_pod_security_group_name \ --description "My pod security group" my_pod_security_group_id=$(aws ec2 describe-security-groups \ --filters Name=group-name,Values=$my_pod_security_group_name \ --query 'SecurityGroups[].GroupId' \ --output text) echo $my_pod_security_group_id
    3. Lassen Sie Datenverkehr über TCP- und UDP-Port 53 von der pod-Sicherheitsgruppe zu, die Sie im vorherigen Schritt für Ihre Cluster-Sicherheitsgruppe erstellt haben. Wenn der DNS-Datenverkehr von Ihrem pod an eine andere Sicherheitsgruppe als Ihre Cluster-Sicherheitsgruppe geleitet werden soll, dann ersetzen Sie $my_cluster_security_group_id durch Ihre eigene Sicherheitsgruppen-ID. Notieren Sie die für SecurityGroupRuleId in der Ausgabe zurückgegebenen Werte. Sie werden sie in einem späteren Schritt noch benötigen.

      aws ec2 authorize-security-group-ingress \ --group-id $my_cluster_security_group_id \ --protocol tcp --port 53 --source-group $my_pod_security_group_id aws ec2 authorize-security-group-ingress \ --group-id $my_cluster_security_group_id \ --protocol udp --port 53 --source-group $my_pod_security_group_id
    4. Lassen Sie eingehenden Datenverkehr zu Ihrer pod-Sicherheitsgruppe von jedem pod, mit dem die Sicherheitsgruppe verknüpft ist, über jedes Protokoll und jeden Port zu. Die Sicherheitsgruppe verfügt über eine standardmäßige ausgehende Regel, die ausgehenden Datenverkehr von den pods, mit denen Ihre Sicherheitsgruppe verknüpft ist, über jedes Protokoll und jeden Port an jedes Ziel zulässt.

      aws ec2 authorize-security-group-ingress \ --group-id $my_pod_security_group_id \ --protocol -1 --port -1 --source-group $my_pod_security_group_id
  2. Erstellen Sie einen Kubernetes-Namespace zum Bereitstellen von Ressourcen.

    kubectl create namespace my-namespace
  3. Stellen Sie ein Amazon EKS SecurityGroupPolicy in Ihrem Cluster bereit.

    1. Speichern Sie die folgende Beispielsicherheitsrichtlinie in einer Datei mit dem Namen my-security-group-policy.yaml. Sie können podSelector durch serviceAccountSelector ersetzen, wenn Sie pods lieber basierend auf Servicekontomarkierungen auswählen möchten. Sie müssen den einen oder anderen Selektor angeben. Ein leeres podSelector (Beispiel: podSelector: {}) wählt alle pods im Namespace aus. Ein leeres serviceAccountSelector wählt alle Servicekonten im Namespace aus. Sie müssen 1-5 Sicherheitsgruppen-IDs für groupIds angeben. Falls Sie mehr als eine ID angeben, gilt die Kombination aller Regeln in allen Sicherheitsgruppen für die ausgewählten pods. Ersetzen Sie sg-05b1d815d1EXAMPLE mit der ID der Sicherheitsgruppe, die Sie in einem vorherigen Schritt notiert haben, als Sie die Sicherheitsgruppe für Ihre pod erstellt haben.

      apiVersion: vpcresources.k8s.aws/v1beta1 kind: SecurityGroupPolicy metadata: name: my-security-group-policy namespace: my-namespace spec: podSelector: matchLabels: role: my-role securityGroups: groupIds: - sg-05b1d815d1EXAMPLE
      Wichtig

      Die Sicherheitsgruppe oder -gruppen, die Sie für Ihre pods angeben, müssen die folgenden Kriterien erfüllen:

      • Sie müssen vorhanden sein. Wenn sie nicht vorhanden sind, bleibt Ihr pod im Erstellungsprozess hängen, wenn Sie einen pod bereitstellen, der dem Selektor entspricht. Wenn Sie den pod beschreiben, wird eine Fehlermeldung ähnlich der folgenden angezeigt: An error occurred (InvalidSecurityGroupID.NotFound) when calling the CreateNetworkInterface operation: The securityGroup ID 'sg-05b1d815d1EXAMPLE' does not exist.

      • Sie müssen eingehende Kommunikation von der Cluster-Sicherheitsgruppe (für kubelet) über alle Ports zulassen, für die Sie Probes konfiguriert haben.

      • Sie müssen ausgehende Kommunikation über die TCP- und UDP-Ports 53 an eine Sicherheitsgruppe zulassen, die pods zugewiesen sind, auf denen CoreDNS ausgeführt wird. Die Sicherheitsgruppe für Ihre CoreDNS-pods muss eingehenden Datenverkehr über TCP- und UDP-Port 53 von Ihrer Sicherheitsgruppe zulassen.

      • Sie müssen über notwendige Regeln für eingehenden und ausgehenden Datenverkehr verfügen, um mit anderen pods zu kommunizieren.

      • Wenn Sie die Sicherheitsgruppe mit Fargate verwenden, stellen Sie sicher, dass sie über Regeln verfügen, die es den pods ermöglichen, mit der Kubernetes-Steuerebene zu kommunizieren. Am einfachsten erreichen Sie dies, indem Sie die Cluster-Sicherheitsgruppe als eine der Sicherheitsgruppen angeben.

      Sicherheitsgruppenrichtlinien gelten nur für neu geplante pods. Sie haben keinen Einfluss auf laufende pods.

    2. Die Richtlinie bereitstellen.

      kubectl apply -f my-security-group-policy.yaml
  4. Stellen Sie eine Beispielanwendung mit einem Label bereit, das dem my-role-Wert für podSelector entspricht, den Sie im vorherigen Schritt angegeben haben.

    1. Speichern Sie den folgenden Inhalt in einer Datei mit dem Namen sample-application.yaml.

      apiVersion: apps/v1 kind: Deployment metadata: name: my-deployment namespace: my-namespace labels: app: my-app spec: replicas: 4 selector: matchLabels: app: my-app template: metadata: labels: app: my-app role: my-role spec: terminationGracePeriodSeconds: 120 containers: - name: nginx image: public.ecr.aws/nginx/nginx:1.21 ports: - containerPort: 80 --- apiVersion: v1 kind: Service metadata: name: my-app namespace: my-namespace labels: app: my-app spec: selector: app: my-app ports: - protocol: TCP port: 80 targetPort: 80
    2. Stellen Sie die Anwendung mit dem folgenden Befehl bereit. Wenn Sie die Anwendung bereitstellen, entspricht das Amazon VPC CNI plugin for Kubernetes der role-Markierung und die Sicherheitsgruppen, die Sie im vorherigen Schritt angegeben haben, werden auf den pod angewendet.

      kubectl apply -f sample-application.yaml
      Anmerkung
      • Wenn Ihr pod im Waiting-Zustand hängen bleibt und Sie Insufficient permissions: Unable to create Elastic Network Interface. sehen, wenn Sie den pod beschreiben, bestätigen Sie, dass Sie die IAM-Richtlinie in einem vorherigen Schritt zur IAM-Cluster-Rolle hinzugefügt haben.

      • Wenn Ihr pod im Status Pending feststeckt, überprüfen Sie, ob Ihr Knoten-Instance-Typ limits.go aufgeführt ist, und dass die maximale Anzahl der vom Instance-Typ unterstützten Zweigstellennetzwerkschnittstellen multipliziert mit der Anzahl der Knoten in Ihrer Knotengruppe noch nicht erreicht wurde. Eine m5.large-Instance unterstützt beispielsweise neun Zweigstellen-Netzwerkschnittstellen. Wenn Ihre Knotengruppe fünf Knoten hat, können maximal 45 Zweigstellen-Netzwerkschnittstellen für die Knotengruppe erstellt werden. Der 46. pod, den Sie bereitstellen möchten, bleibt im Pending-Zustand, bis ein anderer pod mit zugehörigen Sicherheitsgruppen gelöscht wird.

      Wenn Sie kubectl describe pod my-deployment-xxxxxxxxxx-xxxxx -n my-namespace ausführen und eine Meldung ähnlich der folgenden Meldung angezeigt wird, kann sie problemlos ignoriert werden. Diese Meldung kann erscheinen, wenn das CNI-Plug-In versucht, das Host-Netzwerk einzurichten, und dies fehlschlägt, während die Netzwerkschnittstelle erstellt wird. Das CNI-Plug-In protokolliert dieses Ereignis, bis die Netzwerkschnittstelle erstellt wird.

      Failed to create pod sandbox: rpc error: code = Unknown desc = failed to set up sandbox container "e24268322e55c8185721f52df6493684f6c2c3bf4fd59c9c121fd4cdc894579f" network for pod "my-deployment-5df6f7687b-4fbjm": networkPlugin cni failed to set up pod "my-deployment-5df6f7687b-4fbjm-c89wx_my-namespace" network: add cmd: failed to assign an IP address to container

      Die maximale Anzahl von pods, die auf dem Instance-Typ ausgeführt werden können, darf nicht überschritten werden. Eine Liste der maximalen Anzahl von pods, die Sie auf jedem Instance-Typ ausführen können, finden Sie unter eni-max-pods.txt auf GitHub. Wenn Sie einen pod mit zugeordneten Sicherheitsgruppen oder den Knoten löschen, auf dem der pod ausgeführt wird, löscht der VPC-Ressourcen-Controller die Zweigstellennetzwerkschnittstelle. Wenn Sie einen Cluster mit pods löschen, die pods für Sicherheitsgruppen verwenden, löscht der Controller die Zweigstellennetzwerkschnittstellen nicht, sodass Sie sie selbst löschen müssen.

  5. Zeigen Sie die pods an, die mit der Beispielanwendung bereitgestellt wurden. Für den Rest dieses Themas wird dieses Terminal als TerminalA bezeichnet.

    kubectl get pods -n my-namespace -o wide

    Die Beispielausgabe lautet wie folgt.

    NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES my-deployment-5df6f7687b-4fbjm 1/1 Running 0 7m51s 192.168.53.48 ip-192-168-33-28.region-code.compute.internal <none> <none> my-deployment-5df6f7687b-j9fl4 1/1 Running 0 7m51s 192.168.70.145 ip-192-168-92-33.region-code.compute.internal <none> <none> my-deployment-5df6f7687b-rjxcz 1/1 Running 0 7m51s 192.168.73.207 ip-192-168-92-33.region-code.compute.internal <none> <none> my-deployment-5df6f7687b-zmb42 1/1 Running 0 7m51s 192.168.63.27 ip-192-168-33-28.region-code.compute.internal <none> <none>
  6. Öffnen Sie in einem separaten Terminal einen der pods. Für den Rest dieses Themas wird dieses Terminal als TerminalB bezeichnet. Ersetzen Sie 5df6f7687b-4fbjm mit der ID eines der pods, die Sie in der Ausgabe im vorherigen Schritt erhalten haben.

    kubectl exec -it -n my-namespace my-deployment-5df6f7687b-4fbjm -- /bin/bash
  7. Überprüfen Sie in der Shell von TerminalB, dass die Beispielanwendung funktioniert.

    curl my-app

    Die Beispielausgabe lautet wie folgt.

    <!DOCTYPE html> <html> <head> <title>Welcome to nginx!</title> ...

    Sie haben diese Ausgabe erhalten, weil alle pods, auf denen die Anwendung ausgeführt wird, mit der Sicherheitsgruppe verknüpft sind, die Sie erstellt haben. Diese Gruppe enthält eine Regel, die den gesamten Datenverkehr zwischen allen pods zulässt, mit denen die Sicherheitsgruppe verknüpft ist. DNS-Datenverkehr wird von dieser Sicherheitsgruppe an die Cluster-Sicherheitsgruppe übertragen, die mit Ihren Knoten verknüpft ist. Auf den Knoten werden CoreDNS-pods ausgeführt, für die Ihr pods eine Namenssuche durchgeführt hat.

  8. Entfernen Sie von TerminalA aus die Sicherheitsgruppenregeln, die die DNS-Kommunikation mit der Cluster-Sicherheitsgruppe ermöglichen, aus Ihrer Sicherheitsgruppe. Wenn Sie die DNS-Regeln in einem der vorherigen Schritte nicht zur Cluster-Sicherheitsgruppe hinzugefügt haben, ersetzen Sie $my_cluster_security_group_id mit der ID der Sicherheitsgruppe, in der Sie die Regeln erstellt haben. Ersetzen Sie sgr-0407e21efdEXAMPLE und sgr-04dedf9701EXAMPLE mit den IDs der Sicherheitsgruppenregeln, die Sie in einem vorherigen Schritt notiert haben.

    aws ec2 revoke-security-group-ingress --group-id $my_cluster_security_group_id --security-group-rule-ids sgr-0407e21efdEXAMPLE aws ec2 revoke-security-group-ingress --group-id $my_cluster_security_group_id --security-group-rule-ids sgr-04dedf9701EXAMPLE
  9. Versuchen Sie über TerminalB noch einmal, auf die Anwendung zuzugreifen.

    curl my-app

    Der Versuch schlägt fehl, weil der pod nicht mehr auf die CoreDNS-pods zugreifen kann, denen die Cluster-Sicherheitsgruppe zugeordnet ist. Die Cluster-Sicherheitsgruppe verfügt nicht mehr über die Sicherheitsgruppenregeln, die eine DNS-Kommunikation von der Sicherheitsgruppe, die Ihrem pod zugeordnet ist, erlauben.

    Wenn Sie versuchen, über die IP-Adressen auf die Anwendung zuzugreifen, die für einen der pods in einem vorherigen Schritt zurückgegeben wurden, erhalten Sie dennoch eine Antwort, da zwischen pods, denen die Sicherheitsgruppe zugeordnet ist, alle Ports erlaubt sind, und eine Namenssuche daher nicht erforderlich ist.

  10. Wenn Sie mit dem Experimentieren fertig sind, können Sie die Beispiel-Sicherheitsgruppenrichtlinie, die Anwendung und die Sicherheitsgruppe, die Sie erstellt haben, mit den folgenden Befehlen entfernen.

    kubectl delete namespace my-namespace aws ec2 delete-security-group --group-id $my_pod_security_group_id