启用RBAC的AKS集群中服务主体获system:masters角色是否合理?
问题解答:未集成AAD的AKS中服务主体获取管理员权限的原因与正确权限管控方式
一、当前行为的本质:是预期但不符合权限管控需求的
你遇到的情况是预期行为,但这并不意味着这是正确的细粒度权限管控方式,核心原因如下:
- 未集成Azure AD(AAD)的AKS集群,默认依赖静态管理员证书完成Kubernetes身份验证。
az aks get-credentials命令的核心作用是从AKS控制平面拉取集群管理员级别的kubeconfig凭证——只要执行该命令的Azure身份(无论是你的用户账户还是服务主体)拥有AKS集群的Microsoft.ContainerService/managedClusters/listClusterAdminCredentials/action权限(大部分AKS相关的Azure RBAC角色,比如Contributor、AKS Cluster Admin都包含这个权限),就能拿到带有O=system:masters的管理员证书,直接获得全集群权限。 - 你给服务主体分配的AKS特定角色是Azure层面的RBAC权限,它管控的是该服务主体对AKS集群资源本身的操作(比如修改集群规模、删除集群),而非Kubernetes集群内部的资源访问权限。这两个RBAC体系完全独立,不能通过Azure RBAC控制K8s内部的权限。
二、正确的权限管控方案
要实现不同主体的权限区分,必须采用以下两种方式之一:
1. 集成AAD到AKS(推荐)
这是AKS实现细粒度RBAC的标准方案,集成后:
- Kubernetes可以直接识别Azure AD身份(用户、服务主体)
- 你可以通过Kubernetes的
Role/ClusterRole定义具体权限,再通过RoleBinding/ClusterRoleBinding将权限绑定到对应的AAD身份(用户组、服务主体) - 此时执行
az aks get-credentials --admin才会获取管理员凭证,不加--admin参数时,会获取对应AAD身份的受限凭证,K8s会根据绑定的RBAC规则管控访问权限
2. 手动使用Kubernetes ServiceAccount(无AAD集成时的替代方案)
如果暂时无法集成AAD,可以通过Kubernetes原生的ServiceAccount实现细粒度权限:
- 创建专用ServiceAccount:
kubectl create serviceaccount <your-sa-name> -n <target-namespace> - 定义符合需求的
Role(命名空间级)或ClusterRole(集群级),比如仅允许读取指定命名空间的Pod:apiVersion: rbac.authorization.k8s.io/v1 kind: Role metadata: namespace: <target-namespace> name: pod-reader rules: - apiGroups: [""] resources: ["pods"] verbs: ["get", "list"] - 创建
RoleBinding将ServiceAccount与上述Role绑定:apiVersion: rbac.authorization.k8s.io/v1 kind: RoleBinding metadata: name: read-pods namespace: <target-namespace> subjects: - kind: ServiceAccount name: <your-sa-name> namespace: <target-namespace> roleRef: kind: Role name: pod-reader apiGroup: rbac.authorization.k8s.io - 获取ServiceAccount的token并配置到kubeconfig中,使用该token访问集群,此时权限会严格遵循绑定的RBAC规则。
三、总结
- 未集成AAD时,
az aks get-credentials默认返回管理员凭证是预期行为,但无法实现权限区分 - 要区分主体身份并管控K8s内部权限,必须集成AAD,或使用Kubernetes ServiceAccount配合原生RBAC规则
- Azure RBAC与Kubernetes RBAC是独立体系,前者管集群资源的Azure层面操作,后者管K8s内部资源访问
内容的提问来源于stack exchange,提问作者GPuri
相关产品推荐
相关产品推荐

