notes 2026-08-07 · 5 min read

Kubernetes for Pentesters: RBAC, Secrets and Pods

Kubernetes pentesting from inside a Pod: ServiceAccount identity, the RBAC verbs that matter, Secrets, pods/exec, node access and cloud identity.

Kubernetes for Pentesters: RBAC, Secrets and Pods

Getting a shell inside a Pod answers one question. The real pentest starts when you discover which identity came with that shell.

Kubernetes is a control API.

Pods, Secrets and Roles are objects inside that API. So are ServiceAccounts, Nodes and Deployments.

Anyone controlling an identity with enough permission can ask the cluster to perform actions on their behalf.

The examples below assume a lab cluster or an authorized penetration test.

Kubernetes attack surface

First find out where you are

Inside a container:

1
2
3
4
id
hostname
cat /proc/1/cgroup 2>/dev/null
mount

Then I look for Kubernetes-specific material:

1
ls -la /var/run/secrets/kubernetes.io/serviceaccount/

A normal Pod may have a projected ServiceAccount token mounted in the filesystem.

In modern Kubernetes versions, those tokens are usually short-lived, bound to the Pod, and rotated automatically.

That is a large improvement over older static tokens.

They are still valid credentials while the Pod exists and the token remains valid.

ServiceAccount is the workload identity

Every namespace has a default ServiceAccount.

If a Pod does not specify another one, it normally receives that default identity.

A ServiceAccount does not automatically receive administrative privilege.

With RBAC enabled, default typically has little beyond basic discovery access granted to authenticated principals unless additional bindings exist.

Finding a token therefore does not mean finding cluster-admin.

The next question is what that token can do.

Check permissions before attempting actions

With kubectl configured for the current identity:

1
kubectl auth can-i --list

Or test one action:

1
kubectl auth can-i get secrets -n app

This avoids blind attempts.

RBAC uses verbs such as get, list, watch and create. It also uses update, patch, delete and specialized verbs.

The combination of verb, resource, and scope defines capability.

RBAC becomes an attack path when permissions connect

Reading Secrets is more than listing names

Kubernetes Secrets may hold passwords, tokens, keys, and registry credentials.

Their values often appear Base64-encoded in the API.

Base64 does not protect sensitive data.

Example:

1
kubectl get secret db-credentials -n app -o yaml

If the identity has get access to that Secret, the data is exposed.

There is an important nuance.

Kubernetes documentation warns that list or watch on Secrets can expose Secret data, not just metadata.

Read-only access to Secrets is still sensitive access.

Creating Pods can be almost as powerful as reading Secrets

Assume you cannot run:

1
kubectl get secrets

but you can create Pods in the namespace.

If an existing workload has a mountable Secret or privileged ServiceAccount, workload creation may provide an indirect route.

HostPath, privileged containers, node selectors, and other settings matter too.

Admission policies and Pod Security Standards can block many paths.

RBAC alone cannot express every safe PodSpec restriction.

Kubernetes security guidance specifically treats workload creation permission as sensitive.

pods/exec gives execution inside an existing workload

If your identity can run:

1
kubectl exec -it pod-name -- /bin/sh

you receive the context of that container.

That may include mounted files.

Secrets.

Tokens.

Cloud credentials.

Sockets.

Impact depends on the Pod selected.

exec in a low-privileged application is one thing.

exec in a controller with a broad ServiceAccount is another.

RBAC has especially sensitive verbs

bind can allow creation of bindings to Roles or ClusterRoles under certain conditions.

escalate can allow roles to be created or changed beyond the caller’s own permissions.

impersonate allows requests to be made as another principal when authorized.

Those verbs deserve priority.

I also inspect who can modify RoleBindings and ClusterRoleBindings.

Permission to manage RBAC may itself be the escalation path.

Namespace scope matters

A RoleBinding grants access in the namespace where it exists.

A ClusterRoleBinding can grant cluster-wide access.

A ClusterRole can also be referenced by a RoleBinding and remain limited to that binding’s namespace.

This distinction prevents a lot of incorrect analysis.

The name ClusterRole does not guarantee access to every namespace.

The binding determines effective scope.

Node access changes the problem

Kubelet runs on every Node.

Nodes also have credentials and access to workloads.

If an attacker controls a Node, reads its filesystem, or reaches an unsafe administrative interface, Pods and authentication material on that Node may become reachable.

Container runtime sockets matter here.

containerd.sock.

docker.sock in older environments.

CRI endpoints.

Control of the runtime may cross the boundary of a single container.

Cloud identity sits close to the cluster

EKS, AKS, and GKE connect Kubernetes identities to cloud identities through different mechanisms.

A workload may receive an AWS IAM Role, Azure Managed Identity, or Google Cloud service account.

The pentest therefore does not end at the Kubernetes API.

Check whether the Pod also carries cloud identity.

A ServiceAccount with minimal RBAC may still map to a powerful AWS role through workload identity.

Both authorization models need testing.

NetworkPolicy is a separate layer

NetworkPolicy controls Pod traffic when the CNI supports and enforces it.

Without policy, a cluster may allow broad communication by default.

NetworkPolicy does not control Kubernetes API authorization.

A Pod unable to connect directly to a database may still hold a ServiceAccount capable of reading the database Secret.

Network and identity are separate layers.

A testing method that works

I build four maps.

Container context.

Kubernetes identity.

RBAC and reachable objects.

External identity, especially cloud.

Then I connect them.

Pod compromises ServiceAccount.

ServiceAccount creates workload.

Workload mounts Secret.

Secret reveals database credentials.

Or:

Pod compromises workload identity.

Workload identity accesses S3.

That graph is the pentest.

Kubernetes pentest method

Hardening that closes paths

Create dedicated ServiceAccounts for workloads.

Set automountServiceAccountToken to false when the application does not need the API.

Use short-lived projected tokens.

Avoid static tokens.

Apply least privilege in RBAC.

Restrict create, patch and update. Treat bind, escalate and impersonate as sensitive too.

Protect Secrets with encryption at rest and minimal access.

Enforce Pod Security Standards and admission controls.

Use NetworkPolicies.

Review cloud workload identities.

A secure cluster limits what a workload can ask the control plane to do after the container itself has already been compromised.

References

Kubernetes, Service Accounts.

Kubernetes, Security Checklist.

Kubernetes, RBAC Good Practices.

Kubernetes, Good practices for Kubernetes Secrets.

This post is licensed under CC BY 4.0 by the author.