3. ResourceQuota YAML 定义与实战:YAML字段详解、创建ResourceQuota、验证配额生效

3.1 ResourceQuota 核心概念与作用域

ResourceQuota 是 Kubernetes 内置的准入控制机制,用于限制命名空间(Namespace)级别的资源消耗总量。它通过一组配额规则,确保单个租户或团队不会过度占用集群资源,是实现多租户隔离与资源公平调度的基础组件。

核心原则: ResourceQuota 作用于命名空间级别,一旦创建,该命名空间内所有 Pod 的资源配置(requests/limits)总和不得超过配额上限。配额检查发生在 Pod 创建或更新阶段,违反配额的操作将被 API Server 拒绝。

3.2 ResourceQuota YAML 字段详解

一个标准的 ResourceQuota 资源定义包含以下关键字段,下表列出了最常用的配额项及其含义:

字段路径 类型 说明 示例值
apiVersion string API 版本,固定为 v1 v1
kind string 资源类型,固定为 ResourceQuota ResourceQuota
metadata.name string 配额名称,在命名空间内唯一 quota-compute
metadata.namespace string 配额生效的目标命名空间 team-alpha
spec.hard map[string]Quantity 硬性配额上限,资源名称与数量的键值对 requests.cpu: "4"
spec.scopes []string 可选,限定配额生效的 Pod 范围(如 BestEffort、NotTerminating) ["NotTerminating"]

常用配额键(spec.hard 中的 key)说明:

  • 计算资源:requests.cpu、requests.memory、limits.cpu、limits.memory
  • 存储资源:requests.storage、persistentvolumeclaims
  • 对象数量:pods、services、configmaps、secrets、replicationcontrollers
  • 扩展资源:requests.nvidia.com/gpu(自定义资源需先注册)
注意: 如果只设置 limits.cpu 而不设置 requests.cpu,则 Pod 的 CPU request 默认为 0,可能导致调度器低估实际负载。建议同时设置 requests 和 limits 配额,或使用 LimitRange 配合默认值。

3.3 创建 ResourceQuota 实战

以下步骤演示如何创建一个包含 CPU、内存和 Pod 数量限制的 ResourceQuota,并部署测试 Pod 验证配额生效。

步骤 1:编写 ResourceQuota YAML

apiVersion: v1
kind: ResourceQuota
metadata:
  name: quota-compute-strict
  namespace: team-alpha
spec:
  hard:
    requests.cpu: "2"
    requests.memory: "4Gi"
    limits.cpu: "4"
    limits.memory: "8Gi"
    pods: "5"

步骤 2:创建命名空间与 ResourceQuota

# 创建命名空间
kubectl create namespace team-alpha

# 创建 ResourceQuota
kubectl apply -f quota-compute-strict.yaml

# 查看配额详情
kubectl get resourcequota quota-compute-strict -n team-alpha -o yaml

步骤 3:部署测试 Pod 验证配额

# 创建一个符合配额的 Pod(requests: 1CPU/2Gi, limits: 2CPU/4Gi)
kubectl run pod-ok --image=nginx --requests='cpu=1,memory=2Gi' --limits='cpu=2,memory=4Gi' -n team-alpha

# 尝试创建超出配额的 Pod(requests: 2CPU/3Gi,累计超过 CPU request 配额)
kubectl run pod-over --image=nginx --requests='cpu=2,memory=3Gi' --limits='cpu=3,memory=6Gi' -n team-alpha

第二个 Pod 创建失败,返回类似以下错误:

Error from server (Forbidden): pods "pod-over" is forbidden: exceeded quota: quota-compute-strict, requested: requests.cpu=2, used: requests.cpu=1, limited: requests.cpu=2
关键验证命令:
  • kubectl describe quota quota-compute-strict -n team-alpha — 查看配额使用量(Used)与上限(Hard)
  • kubectl get quota --all-namespaces — 列出所有命名空间的配额
  • kubectl get pods -n team-alpha --field-selector=status.phase!=Running — 检查被拒绝的 Pod

3.4 ResourceQuota 生效流程与架构

下图展示了 ResourceQuota 在 Pod 创建过程中的准入控制流程:

ResourceQuota 准入控制流程 用户提交 Pod API Server 接收请求 准入控制器链 ResourceQuota 检查 配额足够 → 允许 配额不足 → 拒绝 检查逻辑 累计 Used + 新请求 ≤ Hard 任一资源超限 → 拒绝

3.5 多维度配额组合与 Scope 限定

ResourceQuota 支持通过 spec.scopes 字段对不同类型的 Pod 进行差异化配额管理。常见的 Scope 包括:

Scope 名称 描述 适用场景
BestEffort 仅匹配 QoS 为 BestEffort 的 Pod(无 requests/limits) 限制低优先级批处理任务
NotBestEffort 匹配 QoS 非 BestEffort 的 Pod 保障在线服务的资源配额
Terminating 匹配设置了 activeDeadlineSeconds 的 Pod 限制有超时时间的任务
NotTerminating 匹配未设置 activeDeadlineSeconds 的 Pod 常驻服务(Deployment/StatefulSet)

示例:为 BestEffort Pod 单独设置配额

apiVersion: v1
kind: ResourceQuota
metadata:
  name: quota-besteffort
  namespace: team-alpha
spec:
  hard:
    pods: "10"
  scopes:
    - BestEffort
最佳实践: 建议为每个命名空间创建至少两个 ResourceQuota:一个用于 NotTerminating 的在线服务(设置严格的 CPU/内存 limits),另一个用于 BestEffort 的离线任务(仅限制 Pod 数量)。这样可以避免离线任务抢占在线服务的资源配额。

3.6 验证配额生效的完整命令集

以下命令帮助运维人员快速诊断配额相关问题:

# 查看命名空间所有配额及其使用量
kubectl get quota -n team-alpha

# 详细查看某个配额的使用情况
kubectl describe quota quota-compute-strict -n team-alpha

# 查看命名空间内所有 Pod 的资源请求总和(手动核对)
kubectl get pods -n team-alpha -o=custom-columns=NAME:.metadata.name,CPU_REQ:.spec.containers[*].resources.requests.cpu,MEM_REQ:.spec.containers[*].resources.requests.memory

# 查看准入控制器是否启用 ResourceQuota
kubectl get pod -n kube-system -l component=kube-apiserver -o yaml | grep -A5 "enable-admission-plugins"

# 模拟创建 Pod 但不实际执行(dry-run)
kubectl run test-pod --image=nginx --requests='cpu=1,memory=1Gi' -n team-alpha --dry-run=client -o yaml
常见问题: 如果创建 ResourceQuota 后,命名空间内已有 Pod 超出新配额,这些 Pod 不会被驱逐,但后续的 Pod 更新或扩缩容操作会被拒绝。需要手动调整已有 Pod 的资源请求或删除超限 Pod。

3.7 本章小结

ResourceQuota 是 Kubernetes 多租户资源管控的第一道防线。通过精确的 YAML 字段定义、Scope 限定和配额验证流程,运维团队可以实现命名空间级别的资源硬性隔离。在实际生产环境中,建议结合 LimitRange 设置默认资源请求,并使用 kubectl describe quota 定期监控配额水位,避免因配额不足导致关键服务部署失败。