CKA — RoleBindings & ClusterRoleBindings

5 minute read

CKA Exam Domain

Cluster Architecture, Installation & Configuration — 25%

Roles define permissions. Bindings grant those permissions to users, groups, or ServiceAccounts. Without a binding, a Role does nothing — it’s just a definition sitting in the cluster.

What Is a RoleBinding?

A RoleBinding connects a Role (or ClusterRole) to one or more subjects within a specific namespace.

Think of it this way: the Role is the permission slip, and the RoleBinding is handing that slip to someone.

apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: read-pods-binding
  namespace: dev
subjects:
- kind: User
  name: jane
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: Role
  name: pod-reader
  apiGroup: rbac.authorization.k8s.io

Key fields:

  • subjects — Who gets the permissions (User, Group, or ServiceAccount)
  • roleRef — Which Role to bind (must reference an existing Role or ClusterRole)
  • namespace — The namespace where this binding applies

Important: You cannot change the roleRef after creating a RoleBinding. You must delete and recreate it.

A RoleBinding can reference multiple subjects:

apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: dev-team-binding
  namespace: dev
subjects:
- kind: User
  name: jane
  apiGroup: rbac.authorization.k8s.io
- kind: User
  name: bob
  apiGroup: rbac.authorization.k8s.io
- kind: Group
  name: developers
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: Role
  name: dev-role
  apiGroup: rbac.authorization.k8s.io

What Is a ClusterRoleBinding?

A ClusterRoleBinding connects a ClusterRole to subjects across the entire cluster — all namespaces, including cluster-scoped resources.

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: node-reader-binding
subjects:
- kind: User
  name: admin-user
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: ClusterRole
  name: node-reader
  apiGroup: rbac.authorization.k8s.io

Notice: No namespace in the metadata — ClusterRoleBindings are cluster-wide.

Warning: A ClusterRoleBinding with cluster-admin gives full cluster access. Be very careful with this.

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: emergency-admin
subjects:
- kind: User
  name: break-glass-admin
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: ClusterRole
  name: cluster-admin
  apiGroup: rbac.authorization.k8s.io

RoleBinding vs ClusterRoleBinding

Aspect RoleBinding ClusterRoleBinding
Scope Single namespace Entire cluster
Grants Access To Namespace resources only All resources (cluster + namespaced)
Subject Scope Subjects get access in one namespace Subjects get access everywhere
Can Reference Role or ClusterRole ClusterRole only
metadata.namespace Required Not applicable

Critical CKA fact: A RoleBinding can reference either a Role or a ClusterRole. A ClusterRoleBinding can only reference a ClusterRole.

Subject Types

Bindings grant permissions to subjects. There are three kinds:

Kind Description Example Name namespace field
User Human user (from certificate CN) jane Not applicable
Group Group of users (from certificate O) developers Not applicable
ServiceAccount Pod identity my-sa Required (SA’s namespace)

User Subject

subjects:
- kind: User
  name: jane
  apiGroup: rbac.authorization.k8s.io

Kubernetes doesn’t manage users directly — users come from certificates, OIDC tokens, or external identity providers. The name field matches the certificate’s Common Name (CN).

Group Subject

subjects:
- kind: Group
  name: developers
  apiGroup: rbac.authorization.k8s.io

Groups come from the certificate’s Organization (O) field. Built-in groups include:

  • system:authenticated — All authenticated users
  • system:unauthenticated — All unauthenticated users
  • system:masters — Full admin access (hard-coded, not RBAC)

ServiceAccount Subject

subjects:
- kind: ServiceAccount
  name: my-sa
  namespace: dev

Note the namespace field — ServiceAccounts are namespaced, so you must specify where the SA lives.

Cross-Namespace Binding Trick

This is a very common CKA pattern: use a RoleBinding to bind a ClusterRole within a single namespace.

Why? Instead of creating identical Roles in 10 namespaces, create one ClusterRole and bind it per-namespace with RoleBindings.

# One ClusterRole for read-only access
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: namespace-reader
rules:
- apiGroups: ["", "apps"]
  resources: ["pods", "deployments", "services"]
  verbs: ["get", "list", "watch"]
---
# RoleBinding in dev namespace
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: dev-reader
  namespace: dev
subjects:
- kind: User
  name: jane
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: ClusterRole
  name: namespace-reader
  apiGroup: rbac.authorization.k8s.io
---
# RoleBinding in staging namespace
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: staging-reader
  namespace: staging
subjects:
- kind: User
  name: jane
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: ClusterRole
  name: namespace-reader
  apiGroup: rbac.authorization.k8s.io

Jane gets read-only access in both dev and staging, but NOT in production. One ClusterRole, multiple RoleBindings.

kubectl Commands

# Create a RoleBinding imperatively
kubectl create rolebinding dev-read --role=pod-reader --user=jane -n dev

# Create a RoleBinding for a ServiceAccount
kubectl create rolebinding sa-binding --role=pod-reader --serviceaccount=dev:my-sa -n dev

# Create a ClusterRoleBinding
kubectl create clusterrolebinding admin-bind --clusterrole=cluster-admin --user=admin

# Create a RoleBinding referencing a ClusterRole (cross-namespace trick)
kubectl create rolebinding dev-reader --clusterrole=namespace-reader --user=jane -n dev

# List RoleBindings in a namespace
kubectl get rolebindings -n dev

# Describe a RoleBinding
kubectl describe rolebinding dev-read -n dev

# List all ClusterRoleBindings (excluding system bindings)
kubectl get clusterrolebindings | grep -v system:

# View the full YAML
kubectl get rolebinding dev-read -n dev -o yaml

Practice Questions

Q1. Create a RoleBinding in the testing namespace that binds the Role test-role to user tester.

Show Answer
kubectl create rolebinding test-binding --role=test-role --user=tester -n testing

Or declaratively:

apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: test-binding
  namespace: testing
subjects:
- kind: User
  name: tester
  apiGroup: rbac.authorization.k8s.io
roleRef:
  kind: Role
  name: test-role
  apiGroup: rbac.authorization.k8s.io

Q2. Create a ClusterRoleBinding that gives the group sre-team the ClusterRole cluster-admin.

Show Answer
kubectl create clusterrolebinding sre-admin --clusterrole=cluster-admin --group=sre-team

Q3. How do you grant a ServiceAccount deploy-sa in namespace ci the Role deployer in the same namespace?

Show Answer
kubectl create rolebinding deploy-binding --role=deployer --serviceaccount=ci:deploy-sa -n ci

Note the --serviceaccount format: namespace:name.

Q4. You want user jane to have read-only access to Pods in 5 different namespaces. What’s the most efficient RBAC approach?

Show Answer
  1. Create a single ClusterRole with get/list/watch on Pods
  2. Create a RoleBinding in each of the 5 namespaces referencing that ClusterRole

This uses the cross-namespace binding pattern. One ClusterRole definition, five RoleBindings — much cleaner than creating five identical Roles.

kubectl create clusterrole pod-reader --verb=get,list,watch --resource=pods
kubectl create rolebinding jane-pods --clusterrole=pod-reader --user=jane -n ns1
kubectl create rolebinding jane-pods --clusterrole=pod-reader --user=jane -n ns2
kubectl create rolebinding jane-pods --clusterrole=pod-reader --user=jane -n ns3
kubectl create rolebinding jane-pods --clusterrole=pod-reader --user=jane -n ns4
kubectl create rolebinding jane-pods --clusterrole=pod-reader --user=jane -n ns5

Q5. Can you change the roleRef in an existing RoleBinding?

Show Answer

No. The roleRef field is immutable after creation. If you need to change which Role a binding points to, you must:

  1. Delete the existing RoleBinding
  2. Create a new one with the correct roleRef
kubectl delete rolebinding old-binding -n dev
kubectl create rolebinding new-binding --role=new-role --user=jane -n dev

This is a deliberate design choice — it ensures bindings maintain a clear audit trail.

Updated: