Kubernetes for Pentesters: Part 1

In the first section of this multi-part practical guide, I’ll introduce you to Kubernetes (K8s) from a penetration testing perspective, including basic information, vocabulary, and how to identify and explore Kubernetes instances. Stay tuned for the next installment, where I’ll detail more vulnerabilities and attack paths.
To begin, let’s discuss what Kubernetes is and some of the terminology you’ll need to know. K8s is an open-source system for automating deployment and management of containerized applications across multiple servers (known as a cluster). There is an official glossary available, but here are several key terms to make note of:
- Pod - The smallest object of the Kubernetes ecosystem, a group of containers running together on your cluster.
- Node - What pods run on, each with a kubelet and kube-proxy.
- Kubelet - Uses the Kubernetes API server to make sure pods are running; registers and reports nodes within a cluster.
- Kube-proxy - A proxy that runs on each node in a cluster, maintaining and allowing network communication.
- Cluster - A group of nodes (made up of a control panel node and a set of worker nodes) that run containerized applications.
- Container - Packages an application and dependencies in an optimized way, most often as microservices.
- etcd - A distributed key-value store for managing configuration, state, and metadata.
- Kubectl - A command-line tool for communicating with a Kubernetes API server.
- Kubernetes API Server - Front-end for the cluster, allowing other components to interact. Additionally, configures valid data for API objects.
- Kube-scheduler - Default option for scheduling pods onto nodes.
- Namespace - A virtual cluster allowing for provisioning of resources and establishing scope for pods, services, and deployments using unique naming.
Next, let's discuss kubectl, your main tool for interfacing with K8s instances. This command-line tool is easily installed using Homebrew:
brew install kubectl
or
brew install kubernetes-cli

In order for kubectl to find and access a Kubernetes cluster, it needs a kubeconfig file.

Check that kubectl is properly configured by getting the cluster state:
kubectl cluster-info
Some common commands:
List all pods across all namespaces: kubectl get pods -A
Get secret: kubectl get secrets
Get services: kubectl get services
Version: kubectl version
Now that we have the basics down, we can start to explore K8s reconnaissance and common vulnerabilities associated Kubernetes instances. We’ll start with information disclosure-type issues. Plenty of information can be found via search on crt.sh and Google, searching for subdomains like"k8s.*.com”. Additionally, search for "k8s.%.com" + github and look for YAML files that contain that string.
Tools like Censys and Shodan are useful here as well. Below is a list of keywords to search with these tools:
- kubernetesDashboard
- kubernetes
- k8s
- kubernetes master or kubernetes control plane
- openshift
- swarm
- product:etcd
- k8s.io
- apiserver
- k8s_node/k8s-cluster-etcd/kubeadm-master/kubemaster-etcd
- services.kubernetes.kubernetes_dashboard_found

Tools such as the Kubernetes dashboard, Weave Scope, and Lens may be used to manage clusters. These tools enhance functionality and provide visual representations of the Kubernetes instance. Shodan and Censys can also be used to find misconfigured dashboards. These dashboards often require authentication.
If you have targets with Kubernetes in use, you might see the following open ports and services when doing network mapping.
Common exposed ports for Kubernetes clusters:
Port | Process | Description |
443/TCP | kube-apiserver | Kubernetes API port |
2379/TCP | etcd | etcd,etcdAPI |
6666/TCP | etcd | etcd |
4194/TCP | cAdvisor | Container metrics |
6443/TCP | kube-apiserver | Kubernetes API port |
8443/TCP | kube-apiserver | Minikube API port |
8080/TCP | kube-apiserver | Insecure API port |
10250/TCP | kubelet | HTTPS API which allows full mode access |
10255/TCP | kubelet | Unauthenticated read-only HTTP port: pods, running pods and node state |
10256/TCP | kube-proxy | Kube Proxy health check server |
9099/TCP | calico-felix | Health check server for Calico |
6782-4/TCP | weave | Metrics and endpoints |
30000-32767/TCP | NodePort | Proxy to the services |
44134/TCP | Tiller | Helm service listening |
Kube-apiserver is usually hosted on TCP ports 6443 and 443, but also on 8443 in minikube, and 8080 as insecure.
Sample curl requests to kube-apiserver that might reveal useful information:
curl -k https://
curl -k https://
curl -k https://
Sample requests to access etcdAPI that might reveal useful information:
curl -k https://
curl -k https://
etcdctl --endpoints=http://
A common misconfiguration in Kubernetes exposes API endpoints. By navigating to the IP address in a browser, the server may respond with a list of the API paths
https://<CONTROL PLANE IP>:
/api
/api/v1
/apis
/apis/admissionregistration.k8s.io
/apis/apiextensions.k8s.io
/apis/apiextensions.k8s.io
/apis/apiregistration.k8s.io
/apis/apiregistration.k8s.io/v1
/apis/apps
/apis/apps/v1
/apis/authentication.k8s.io
/apis/authentication.k8s.io/v1
/apis/authorization.k8s.io/v1beta
/apis/autoscaling
/apis/autoscaling/v1
/apis/autoscaling/v1beta
/apis/batch
/apis/batch/v1
/apis/certificates.k8s.io/
/apis/certificates.k8s.io/v1
Additionally, the cAdvisor port might reveal metric information:
curl -k https://
If kube-apiserver allows for unencrypted communication, you can use the following curl request:
curl -k http[s]://
Access to the read-only kubelet port 10255 can expose cluster configuration elements, such as pod names, location of internal files, and other configurations that might be used to identify sensitive information or craft other attacks.
curl -k https://
http://
In the next blog, we’ll discover some more complex vulnerabilities associated with Kubernetes!