欢迎光临
我们一直在努力

Network Policy 实战教程:手把手教你通过白名单锁定 Pod 间的访问权限

在复杂的微服务架构中,限制服务间的访问权限是保障系统安全的关键一环。Kubernetes Network Policy(KNP)允许您定义一组规则,控制 Pod 之间的网络通信。本文将通过实战演练,手把手教您如何通过白名单机制,精确锁定哪些 Pod 可以访问目标服务。

什么是 Network Policy 白名单?

默认情况下,Kubernetes 集群中的所有 Pod 都是可以互相通信的。白名单策略的核心思想是:先拒绝所有流量,然后只允许明确指定的、合法的流量通过。

准备工作

您需要一个支持 Network Policy 的 Kubernetes 集群(例如使用 Calico 或 Cilium 作为 CNI)。我们将创建两个服务 Pod (backendfrontend),并在同一个命名空间内进行测试。

1. 创建命名空间和应用

首先,创建一个名为 security-demo 的命名空间,并在其中部署我们的应用。

# apps.yaml
apiVersion: v1
kind: Namespace
metadata:
  name: security-demo
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: backend
  namespace: security-demo
  labels:
    app: backend
spec:
  selector:
    matchLabels:
      app: backend
  replicas: 1
  template:
    metadata:
      labels:
        app: backend
    spec:
      containers:
      - name: net-utils
        image: busybox
        command: ["sh", "-c", "echo 'Backend Service Running' && sleep 3600"]
        ports:
        - containerPort: 80
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: frontend
  namespace: security-demo
  labels:
    app: frontend
spec:
  selector:
    matchLabels:
      app: frontend
  replicas: 1
  template:
    metadata:
      labels:
        app: frontend
    spec:
      containers:
      - name: net-utils
        image: busybox
        command: ["sleep", "3600"]
---
# 测试用 Pod,用于验证非白名单流量
apiVersion: v1
kind: Pod
metadata:
  name: unauthorized-client
  namespace: security-demo
  labels:
    app: unauthorized
spec:
  containers:
  - name: net-utils
    image: busybox
    command: ["sleep", "3600"]

执行部署:

kubectl apply -f apps.yaml

# 确认 Pod IP
BACKEND_IP=$(kubectl get pod -n security-demo -l app=backend -o jsonpath='{.items[0].status.podIP}')

2. 初始状态测试(开放)

在未应用 Network Policy 之前,所有 Pod 都可以访问 backend

frontend 访问 backend (应该成功):

kubectl exec -n security-demo deployment/frontend -- wget -T 2 -O - $BACKEND_IP:80
# 预计输出: Backend Service Running

实施白名单策略

白名单实现分为两步:默认拒绝(锁门),然后精确放行(开锁)。

3. 默认拒绝所有 Ingress 流量

创建一个 Network Policy,目标是 backend Pod,并拒绝所有进入该 Pod 的流量。当 policyTypes 中列出了 Ingressrules 列表为空时,即实现了默认拒绝。

# 01-default-deny.yaml
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default-deny-backend-ingress
  namespace: security-demo
spec:
  podSelector:
    matchLabels:
      app: backend
  # 仅针对 Ingress 流量生效
  policyTypes:
  - Ingress

应用策略:

kubectl apply -f 01-default-deny.yaml

4. 验证拒绝效果

再次从 frontend 访问 backend (现在应该被阻止):

kubectl exec -n security-demo deployment/frontend -- wget -T 2 -O - $BACKEND_IP:80
# 预计输出: wget: download timed out (连接超时)

5. 实现精确白名单放行

现在,我们只允许拥有标签 app: frontend 的 Pod 访问 backend Pod 的 80 端口。

# 02-whitelist-frontend.yaml
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-frontend-access
  namespace: security-demo
spec:
  podSelector:
    matchLabels:
      app: backend # 目标 Pod (backend)
  policyTypes:
  - Ingress
  rules:
  - from:
    - podSelector:
        matchLabels:
          app: frontend # 允许来自具有此标签的 Pod 的流量
    ports:
    - protocol: TCP
      port: 80

注意: Network Policy 是累加的。应用此策略后,它会与步骤 3 中的默认拒绝策略合并:先拒绝所有,再根据新策略允许特定流量。

应用策略:

kubectl apply -f 02-whitelist-frontend.yaml

6. 最终验证

测试 1: 白名单访问 (Frontend -> Backend)

kubectl exec -n security-demo deployment/frontend -- wget -T 2 -O - $BACKEND_IP:80
# 结果: 成功。输出 'Backend Service Running'

测试 2: 非白名单访问 (Unauthorized Pod -> Backend)

kubectl exec -n security-demo pod/unauthorized-client -- wget -T 2 -O - $BACKEND_IP:80
# 结果: 失败。连接超时,因为该 Pod 不具备 'app: frontend' 标签,被默认拒绝策略阻止。

总结

通过先应用默认拒绝策略(隐式或显式),然后精确定义 fromto 规则,我们成功地在 Kubernetes 中实现了基于 Pod 标签的白名单访问控制。这是保护微服务边界,确保只有授权组件能够互相通信的强大安全实践。

【本站文章皆为原创,未经允许不得转载】:汤不热吧 » Network Policy 实战教程:手把手教你通过白名单锁定 Pod 间的访问权限
分享到: 更多 (0)

评论 抢沙发

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址