3. 多租户模型设计:租户定义、命名空间隔离、资源配额与网络策略基础

在 Kubernetes 集群中实现多租户隔离,核心在于将逻辑租户映射到物理集群资源上,并通过一系列原生机制确保故障域、资源域与安全域的独立。本节将定义租户模型,并深入讲解命名空间隔离、ResourceQuota 与 NetworkPolicy 的基础配置。

3.1 租户定义与模型抽象

租户(Tenant)是集群资源与工作负载的逻辑所有者。在云原生架构中,租户通常对应一个团队、一个项目或一个业务线。租户模型需明确以下属性:

属性 描述 示例值
Tenant ID 全局唯一标识符,用于审计与计费 tenant-001
Namespace 集合 租户独占的命名空间列表 ns-team-alpha-prod, ns-team-alpha-staging
资源配额 CPU、内存、存储、对象数的上限 CPU: 32 cores, Memory: 128Gi
网络策略 入站/出站流量控制规则 仅允许同租户 Namespace 通信
RBAC 绑定 租户管理员与成员的角色绑定 ClusterRoleBinding 或 RoleBinding
设计原则: 每个租户至少拥有一个生产 Namespace 和一个预发 Namespace。禁止跨租户共享 Namespace,这是故障域隔离的底线。

3.2 命名空间隔离:租户的边界墙

Kubernetes Namespace 是隔离的基础单元。每个租户的工作负载、ConfigMap、Secret 都应部署在专属 Namespace 内。命名空间隔离策略如下:

  • 命名规范: <tenant-id>-<environment>,例如 tenant-alpha-prod。
  • 标签注入: 每个 Namespace 必须携带 tenant: <tenant-id> 标签,便于策略匹配与审计。
  • 禁止默认 Namespace: 生产环境禁止使用 default Namespace 部署任何业务负载。
# 创建租户 Namespace 示例
apiVersion: v1
kind: Namespace
metadata:
  name: tenant-alpha-prod
  labels:
    tenant: tenant-alpha
    environment: production
    isolation-tier: high
注意: 命名空间隔离仅提供逻辑分组,不提供网络或资源硬隔离。必须配合 NetworkPolicy 与 ResourceQuota 才能形成完整的多租户故障域。

3.3 资源配额(ResourceQuota):防止租户资源抢占

ResourceQuota 是 Kubernetes 原生资源管控机制,用于限制一个 Namespace 内所有 Pod 的资源总和。在多租户场景下,它为每个租户划定资源上限,避免某个租户的异常流量或错误配置耗尽集群资源,从而保护其他租户的稳定性。

配额类型 作用范围 典型配置
计算资源 CPU / Memory 请求与限制 requests.cpu: "32", limits.memory: "128Gi"
存储资源 PVC 总容量与数量 requests.storage: "500Gi", persistentvolumeclaims: "10"
对象数量 Pod、Service、ConfigMap 等数量 pods: "50", services: "20"
# 租户 ResourceQuota 配置示例
apiVersion: v1
kind: ResourceQuota
metadata:
  name: tenant-alpha-quota
  namespace: tenant-alpha-prod
spec:
  hard:
    requests.cpu: "32"
    requests.memory: "128Gi"
    limits.cpu: "64"
    limits.memory: "256Gi"
    pods: "50"
    persistentvolumeclaims: "10"
    requests.storage: "500Gi"
最佳实践: 为每个租户的每个 Namespace 创建独立的 ResourceQuota。同时设置 LimitRange 来约束单个 Pod 的资源范围,防止单个 Pod 占满整个租户配额。

3.4 网络策略(NetworkPolicy):租户间流量隔离

NetworkPolicy 是 Kubernetes 原生的网络访问控制机制,基于 Pod 标签和 Namespace 选择器实现精细化的流量管控。在多租户架构中,NetworkPolicy 是防止租户间横向移动攻击、保障网络故障域隔离的关键。

基础策略模型包含三类规则:

  • 默认拒绝入站: 拒绝所有非本租户 Namespace 的入站流量。
  • 允许同租户通信: 允许同一租户下不同 Namespace 之间的必要通信。
  • 允许系统组件: 允许监控、日志、DNS 等基础设施组件的访问。
# 租户隔离 NetworkPolicy 示例
apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: tenant-alpha-isolation
  namespace: tenant-alpha-prod
spec:
  podSelector: {}  # 匹配该 Namespace 下所有 Pod
  policyTypes:
  - Ingress
  - Egress
  ingress:
  - from:
    - namespaceSelector:
        matchLabels:
          tenant: tenant-alpha  # 仅允许同租户 Namespace 的流量
    - namespaceSelector:
        matchLabels:
          kubernetes.io/metadata.name: kube-system  # 允许系统组件
  egress:
  - to:
    - namespaceSelector:
        matchLabels:
          tenant: tenant-alpha
    - namespaceSelector:
        matchLabels:
          kubernetes.io/metadata.name: kube-system
关键点: NetworkPolicy 需要 CNI 插件支持(如 Calico、Cilium)。在 etcd 故障场景下,NetworkPolicy 控制器可能失效,因此建议在集群升级前验证策略的持久化状态。

3.5 多租户隔离架构总览

下图展示了基于命名空间、资源配额与网络策略的多租户隔离架构。每个租户拥有独立的 Namespace 集合,ResourceQuota 划定资源边界,NetworkPolicy 控制流量边界,共同构成故障域隔离的基础。

多租户隔离架构总览 租户 A (tenant-alpha) Namespace: tenant-alpha-prod Pod: app-v1 Pod: app-v2 ResourceQuota: CPU 32 / Mem 128Gi Namespace: tenant-alpha-staging Pod: app-dev Pod: db-test ResourceQuota: CPU 16 / Mem 64Gi NetworkPolicy: 仅允许同租户 + kube-system 流量 租户 B (tenant-beta) Namespace: tenant-beta-prod Pod: web Pod: api ResourceQuota: CPU 48 / Mem 192Gi Namespace: tenant-beta-staging Pod: web-dev Pod: cache ResourceQuota: CPU 24 / Mem 96Gi NetworkPolicy: 仅允许同租户 + kube-system 流量 隔离边界

3.6 多租户隔离清单与验证

在集群升级前,必须逐项验证多租户隔离配置的有效性。以下为关键检查项:

检查项 验证方法 预期结果
Namespace 标签完整性 kubectl get ns --show-labels 每个 Namespace 携带 tenant 标签
ResourceQuota 生效 kubectl describe quota -n <ns> 配额已绑定,且当前使用量在限制内
NetworkPolicy 隔离 从跨租户 Pod 发起 curl 测试 连接超时或被拒绝
同租户通信 从同租户不同 Namespace 发起 curl 连接正常
升级前必做: 在 etcd 故障模拟场景中,NetworkPolicy 控制器可能因 etcd 不可用而无法同步最新规则。建议在升级前将关键 NetworkPolicy 规则导出为静态备份,并验证 CNI 插件在 etcd 恢复后的策略重载能力。