4. Role 详解:YAML 结构、命名空间作用域与常用字段

Role 是 Kubernetes RBAC 中最基础的权限单元,用于定义一组权限规则。与 ClusterRole 不同,Role 具有命名空间作用域,即它只能在其所属的命名空间内生效。理解 Role 的 YAML 结构、字段含义和作用域限制,是构建精细化权限模型的第一步。

4.1 Role 的 YAML 结构与核心字段

一个标准的 Role 资源由 apiVersion、kind、metadata 和 rules 四个顶层字段组成。其中 rules 字段是权限定义的核心,它通过一组“动词-资源-资源名称”的规则来描述允许的操作。

📌 核心要点: Role 的 rules 字段是一个数组,每个规则对象包含 apiGroups、resources、verbs 和可选的 resourceNames。规则之间是“或”关系,只要匹配任意一条规则,权限即生效。
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: pod-reader
  namespace: default          # 关键:指定命名空间
rules:
- apiGroups: [""]             # 核心 API 组(空字符串)
  resources: ["pods"]         # 资源类型
  verbs: ["get", "list", "watch"]  # 允许的操作
- apiGroups: ["apps"]
  resources: ["deployments"]
  verbs: ["get", "list"]
  resourceNames: ["web-app"]  # 仅限名为 web-app 的 Deployment

4.2 字段详解与参数对照

字段 类型 说明 示例值
apiGroups []string API 组名称,空字符串 "" 表示核心组(v1),"*" 表示所有 API 组 [""], ["apps"], ["batch"]
resources []string 资源类型,支持子资源(如 pods/log)和通配符 "*" ["pods"], ["deployments/status"]
verbs []string 允许的操作动词,常用:get, list, watch, create, update, patch, delete ["get", "list"]
resourceNames []string 可选字段,限定允许操作的资源名称列表 ["my-pod-1", "my-pod-2"]

4.3 命名空间作用域详解

Role 的命名空间作用域是其与 ClusterRole 最本质的区别。以下通过对比表格和结构图来清晰展示这一特性。

特性 Role ClusterRole
作用域 单个命名空间 集群级别(所有命名空间 + 集群资源)
适用资源 命名空间资源(Pod、Service、ConfigMap 等) 命名空间资源 + 集群资源(Node、PV、Namespace 等)
绑定对象 RoleBinding(同命名空间) RoleBinding 或 ClusterRoleBinding
典型场景 团队隔离、项目级权限 集群管理员、跨命名空间权限
Role 命名空间作用域示意图 Kubernetes 集群 Namespace: production Role: pod-manager rules: pods [get, list, create, delete] Pod: web-1 Pod: web-2 Pod: api-1 ✅ 作用域:仅限 production 命名空间 无法访问其他命名空间的资源 无法访问集群级资源(Node、PV) Namespace: staging Role: pod-viewer rules: pods [get, list, watch] Pod: test-1 Pod: test-2 Pod: db-1 ❌ 无法访问 production 命名空间 即使有相同的资源类型 权限完全隔离

4.4 常用字段组合示例

以下列举几种典型的 Role 配置模式,覆盖了日常使用中最常见的权限场景。

💡 最佳实践: 始终遵循“最小权限原则”,只授予完成工作所必需的最小权限集合。优先使用 resourceNames 字段将权限限定到特定资源实例。

示例 1:只读访问特定命名空间的所有 Pod

apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: pod-reader
  namespace: development
rules:
- apiGroups: [""]
  resources: ["pods"]
  verbs: ["get", "list", "watch"]

示例 2:读写 Deployment 和 Service,但仅限特定名称

apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: app-manager
  namespace: production
rules:
- apiGroups: ["apps"]
  resources: ["deployments"]
  verbs: ["get", "list", "create", "update", "delete"]
  resourceNames: ["frontend", "backend"]
- apiGroups: [""]
  resources: ["services"]
  verbs: ["get", "list", "create", "update", "delete"]
  resourceNames: ["frontend-svc", "backend-svc"]

示例 3:访问子资源(Pod 日志)

apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: pod-log-reader
  namespace: monitoring
rules:
- apiGroups: [""]
  resources: ["pods/log"]
  verbs: ["get", "list"]

4.5 常见错误与避坑指南

  • ❌ 错误: 在 Role 中定义集群资源(如 nodes、persistentvolumes)。
    ✅ 正确: 集群资源必须使用 ClusterRole 定义。
  • ❌ 错误: 忘记在 metadata 中指定 namespace,导致 Role 创建失败或作用域不符合预期。
    ✅ 正确: 始终显式声明 namespace 字段。
  • ❌ 错误: 在 rules 中使用空白的 apiGroups 字段访问 apps/v1 的资源。
    ✅ 正确: 核心 API 组用 "",apps 组用 ["apps"],batch 组用 ["batch"]。
  • ❌ 错误: 将 resourceNames 与 create 动词一起使用,导致创建操作失败。
    ✅ 正确: resourceNames 仅对 get、update、delete 等操作生效,create 操作无法预知资源名称。
Role 规则匹配流程 API 请求到达 检查:请求 Namespace 是否匹配 Role 的 Namespace 遍历 rules:匹配 apiGroups + resources + verbs ✅ 允许(Allow) ❌ 拒绝(Deny)
⚠️ 重要提醒: Role 的规则匹配是“白名单”机制——只有明确允许的操作才会被放行,未定义的任何操作默认拒绝。不要在 Role 中使用通配符 verbs: ["*"] 或 resources: ["*"],除非你完全清楚这样做的安全后果。