你当前正在访问 Microsoft Azure Global Edition 技术文档网站。 如果需要访问由世纪互联运营的 Microsoft Azure 中国技术文档网站,请访问 https://docs.azure.cn

在高级容器网络服务中为容器网络安全设置 FQDN 筛选功能

本文介绍如何在 AKS 群集中设置具有容器网络安全功能的高级容器网络服务。

Prerequisites

  • 具有活动订阅的 Azure 帐户。 如果还没有该订阅,可以在开始前创建一个免费帐户

本文中的步骤所需的最低 Azure CLI 版本为 2.71.0。 运行 az --version 即可查找版本。 如果需要进行安装或升级,请参阅安装 Azure CLI

限制:

  • 部分支持通配符 FQDN 策略。 这意味着可以创建与前导通配符(例如 .example.com)匹配特定模式的策略 ,但不能使用通用通配符()匹配字段上的所有域 spec.egress.toPorts.rules.dns.matchPattern
  • 支持的模式:

    *.example.com - 这允许流量流向 example.com 下的所有子域。

    app*.example.com - 此规则更具体,仅允许流量到 example.com 下以 "app" 开头的子域。

  • 不支持的模式

    * 这会尝试匹配任何域名,不支持。

  • 节点本地 DNS 目前不支持 FQDN 筛选。
  • 不支持 Kubernetes 服务名称。
  • 不支持其他 L7 策略。
  • 处理每秒超过 1,000 个请求时,FQDN Pod 可能会表现出性能下降。
  • 如果禁用高级容器网络服务(ACNS)安全性,将阻止 FQDN 和 L7 策略(HTTP、HTTPS、Kafka 和 gRPC)。
  • 在 Cilium 网络策略中使用时,基于 Alpine 的容器映像可能会遇到 DNS 解析问题。 这是因为 musl libc 的有限搜索域迭代。 若要解决此问题,请使用通配符模式显式定义网络策略 DNS 规则中的所有搜索域,如以下示例所示
rules:
  dns:
  - matchPattern: "*.example.com"
  - matchPattern: "*.example.com.*.*"
  - matchPattern: "*.example.com.*.*.*"
  - matchPattern: "*.example.com.*.*.*.*"
  - matchPattern: "*.example.com.*.*.*.*.*"
- toFQDNs:
  - matchPattern: "*.example.com"

启用高级容器网络服务

若要继续,必须有一个启用了高级容器网络服务的 AKS 群集。

具有高级容器网络服务标志 az aks create--enable-acns 命令创建一个新的 AKS 群集,它具有所有高级容器网络服务功能。 这些功能包括:

  • 容器网络可观测性:提供对流量的见解。 若要了解详细信息,请访问容器网络可观测性

  • 容器网络安全: 提供完全限定域名(FQDN)筛选等安全功能。 若要了解详细信息,请访问容器网络安全

# Set an environment variable for the AKS cluster name. Make sure to replace the placeholder with your own value.
export CLUSTER_NAME="<aks-cluster-name>"

# Create an AKS cluster
az aks create \
    --name $CLUSTER_NAME \
    --resource-group $RESOURCE_GROUP \
    --generate-ssh-keys \
    --location eastus \
    --network-plugin azure \
    --network-dataplane cilium \
    --node-count 2 \
    --enable-acns

在现有群集上启用高级容器网络服务

具有高级容器网络服务标志 az aks update--enable-acns 命令会更新现有的 AKS 群集,使其具有所有高级容器网络服务功能,包括 容器网络可观测性容器网络安全 功能。

注意

只有具有 Cilium 数据平面的群集才支持高级容器网络服务的容器网络安全功能。

az aks update \
    --resource-group $RESOURCE_GROUP \
    --name $CLUSTER_NAME \
    --enable-acns

获取群集凭据

使用 az aks get-credentials 命令获取群集凭据。

az aks get-credentials --name $CLUSTER_NAME --resource-group $RESOURCE_GROUP

使用策略测试连接

本节演示如何观察通过 Cilium 代理强制实施的策略。 向允许的 FQDN 和另一个请求会被阻止的情况发出 DNS 请求。

创建名为 demo-policy.yaml 的文件并粘贴以下 YAML 清单:

注意

在策略中使用 FQDN 时,该字段spec.egress.toPorts.rules.dns.matchPattern是必需的。 本部分告知 Cilium 检查 DNS 查询,并将其与指定的模式匹配。 如果没有此部分,Cilium 仅允许 DNS 流量,并且不检查其内容,以了解哪些 IP 与 FQDN 相关联。 因此,与这些 IP(即非 DNS 流量)的连接会被阻止,因为 Cilium 无法将它们与允许的域相关联。

请务必首先检查 限制 部分。

apiVersion: "cilium.io/v2"
kind: CiliumNetworkPolicy
metadata:
  name: "allow-bing-fqdn"
spec:
  endpointSelector:
    matchLabels:
      app: demo-container
  egress:
    - toEndpoints:
      - matchLabels:
          "k8s:io.kubernetes.pod.namespace": kube-system
          "k8s:k8s-app": kube-dns
      toPorts:
        - ports:
           - port: "53"
             protocol: ANY
          rules:
            dns:
              - matchPattern: "*.bing.com"
    - toFQDNs:
      - matchPattern: "*.bing.com"

指定 YAML 清单的名称并使用 [kubectl apply][kubectl-apply] 应用该名称:

kubectl create ns demo
kubectl apply -f demo-policy.yaml -n demo

创建演示 Pod

创建运行 Bash 的 client Pod:

kubectl run -it client -n demo --image=k8s.gcr.io/e2e-test-images/agnhost:2.43 --labels="app=demo-container" --command -- bash

具有用于测试 FQDN 的实用程序的 shell 应该会打开,并显示以下输出:

If you don't see a command prompt, try pressing enter.
bash-5.0#

在一个单独的窗口中,运行以下命令以获取正在运行的 Pod 的节点。

kubectl get po -n demo --sort-by="{spec.nodeName}" -o wide

输出应类似于以下示例:

NAME     READY   STATUS    RESTARTS   AGE     IP              NODE                                NOMINATED NODE   READINESS GATES
client   1/1     Running   0          5m50s   192.168.0.139   aks-nodepool1-22058664-vmss000001   <none>           <none>

该 Pod 在名为 aks-nodepool1-22058664-vmss000001 的节点上运行。 获取在该节点上运行的 Cilium 代理实例:

kubectl get po -n kube-system -o wide --field-selector spec.nodeName="aks-nodepool1-22058664-vmss000001" | grep "cilium"

预期 cilium-s4x24 应该在输出中。

cilium-s4x24                          1/1     Running   0          47m   10.224.0.4      aks-nodepool1-22058664-vmss000001   <none>           <none>

检查 Cilium 代理

使用 cilium CLI 监视被阻止的流量。

kubectl exec -it -n kube-system cilium-s4x24 -- sh
Defaulted container "cilium-agent" out of: cilium-agent, install-cni-binaries (init), mount-cgroup (init), apply-sysctl-overwrites (init), mount-bpf-fs (init), clean-cilium-state (init), block-wireserver (init)
#

在此 shell 中,运行 cilium monitor -t drop

Listening for events on 2 CPUs with 64x4096 of shared memory
Press Ctrl-C to quit
time="2024-10-08T17:48:27Z" level=info msg="Initializing dissection cache..." subsys=monitor

验证策略

从第一个 shell 中,如策略所指定,创建对允许的 FQDN *.bing.com 的请求。 此请求应成功,并获得代理的允许。

./agnhost connect www.bing.com:80

然后,对一个预期请求会被阻止的 FQDN 创建另一个请求:

./agnhost connect www.example.com:80

Cilium 代理阻止该请求,并显示输出:

xx drop (Policy denied) flow 0xfddd76f6 to endpoint 0, ifindex 29, file bpf_lxc.c:1274, , identity 48447->world: 192.168.0.149:45830 -> 93.184.215.14:80 tcp SYN

由CiliumClusterwideNetworkPolicy(CCNP)支持

CiliumClusterwideNetworkPolicy 支持 FQDN 筛选。

注意

命名空间特定信息 (例如 io.kubernetes.pod.namespace 仅在群集范围内策略中受支持)。

apiVersion: cilium.io/v2
kind: CiliumClusterwideNetworkPolicy
metadata:
  name: allow-bing-fqdn
spec:
  endpointSelector: {} # Applies to all pods in the cluster
  egress:
    - toEndpoints:
      - matchLabels:
          "k8s:io.kubernetes.pod.namespace": kube-system
          "k8s:k8s-app": kube-dns
      toPorts:
        - ports:
           - port: "53"
             protocol: ANY
          rules:
            dns:
              - matchPattern: "*.bing.com"
    - toFQDNs:
      - matchPattern: "*.bing.com"

清理资源

如果不打算使用此应用程序,请使用 az group delete 命令删除本文中创建的其他资源。

  az group delete --name $RESOURCE_GROUP

后续步骤

本操作指南文章介绍了如何为 AKS 群集安装和启用高级容器网络服务的安全功能。