Know Your Cluster
Now that we have a cluster, let's see some important and useful details.
API Server Port
We know that our kubectl commands communicate with the API server in the control plane.
But what is the port that the API server listens on for the incoming queries/requests?
It's 6443.
As we also have a kind cluster, we can check this by:
docker ps
PS D:\Learning\Kubernetes\CKA> docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES fe0d2717cdbf kindest/node:v1.35.0 "/usr/local/bin/entr…" 16 minutes ago Up 16 minutes cka-lab-worker2 ccb9423927f2 kindest/node:v1.35.0 "/usr/local/bin/entr…" 16 minutes ago Up 16 minutes cka-lab-worker af71b642cbbf kindest/node:v1.35.0 "/usr/local/bin/entr…" 16 minutes ago Up 16 minutes 127.0.0.1:53490->6443/tcp cka-lab-control-plane
Nodes
We know that a Kubernetes cluster has a control plane and worker nodes. To see those details:
kubectl get nodes -o wide
PS D:\Learning\Kubernetes\CKA> kubectl get nodes -o wide NAME STATUS ROLES AGE VERSION INTERNAL-IP EXTERNAL-IP OS-IMAGE KERNEL-VERSION CONTAINER-RUNTIME cka-lab-control-plane Ready control-plane 7m9s v1.35.0 172.18.0.2 <none> Debian GNU/Linux 12 (bookworm) 5.15.153.1-microsoft-standard-WSL2 containerd://2.2.0 cka-lab-worker Ready <none> 6m57s v1.35.0 172.18.0.3 <none> Debian GNU/Linux 12 (bookworm) 5.15.153.1-microsoft-standard-WSL2 containerd://2.2.0 cka-lab-worker2 Ready <none> 6m57s v1.35.0 172.18.0.4 <none> Debian GNU/Linux 12 (bookworm) 5.15.153.1-microsoft-standard-WSL2 containerd://2.2.0
What does the output say
- NAME = Node name (kind automatically adds control-plane / worker as suffix to the acutal cluster name)
- STATUS = Node status (Ready means the kubelet is healthy)
- ROLES = Node role (control-plane or worker, workers show none)
- AGE = Node age (time since the node joined the cluster)
- VERSION = Kubernetes version running on the node
- INTERNAL-IP = Node internal IP address (used for communication between nodes kind Docker bridge network)
- EXTERNAL-IP = Node external IP address (used for communication with external clients)
- OS-IMAGE = Operating system image running on the node
- KERNEL-VERSION = Kernel version running on the node
- CONTAINER-RUNTIME = Container runtime used on the node (containerd in this case)
Config or context
The context information is stored in the kubeconfig file which we talked about in the last tutorial.
A context is like a bundle that contains
- cluster (API server + certificates)
- user credentials
- default namespace
We may be working with multiple cluster from our local, context tells us which cluster the kubectl CLI
is currently configured to communicate with.
kubectl config current-context
PS D:\Learning\Kubernetes\CKA> kubectl config current-context kind-cka-lab
Kind updates the kubeconfig file and sets the cluster it created as active target.
Kubernetes components
We learned about the Kubernetes architecure - control plane and worker nodes.
Surprisingly, the control plane components - API server, etcd, controller manager, scheduler, kubeproxy - all run as pods
in the kube-system namespace. A namespace is a logical grouping of the related resources. We will learn about
namespaces going forward.
kubectl get pods -n kube-system -o wide
PS D:\Learning\Kubernetes\CKA> kubectl get pods -n kube-system -o wide NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES coredns-7d764666f9-cbs5l 1/1 Running 0 42m 10.244.0.3 cka-lab-control-plane <none> <none> coredns-7d764666f9-sj5nr 1/1 Running 0 42m 10.244.0.2 cka-lab-control-plane <none> <none> etcd-cka-lab-control-plane 1/1 Running 0 42m 172.18.0.2 cka-lab-control-plane <none> <none> kindnet-9p4ls 1/1 Running 0 42m 172.18.0.2 cka-lab-control-plane <none> <none> kindnet-tksxg 1/1 Running 0 42m 172.18.0.3 cka-lab-worker <none> <none> kindnet-xj6fq 1/1 Running 0 42m 172.18.0.4 cka-lab-worker2 <none> <none> kube-apiserver-cka-lab-control-plane 1/1 Running 0 42m 172.18.0.2 cka-lab-control-plane <none> <none> kube-controller-manager-cka-lab-control-plane 1/1 Running 0 42m 172.18.0.2 cka-lab-control-plane <none> <none> kube-proxy-2df7b 1/1 Running 0 42m 172.18.0.4 cka-lab-worker2 <none> <none> kube-proxy-9q97z 1/1 Running 0 42m 172.18.0.3 cka-lab-worker <none> <none> kube-proxy-xgvbq 1/1 Running 0 42m 172.18.0.2 cka-lab-control-plane <none> <none> kube-scheduler-cka-lab-control-plane 1/1 Running 0 42m 172.18.0.2 cka-lab-control-plane <none> <none>
The API server, etcd, controller manager, scheduler are running on the control plane (master node).
We do not have cloud controller manager component on the contol plane as we did not host our cluster in any of the cloud provider platform.
The networking component kube-proxy runs on all the nodes as it needs to route the traffic from across the pods on different nodes.
But who runs these pods??
The kubelet on the control plane node is responsible for running these control plane components.
The manifest files for these control plane components are stored in /etc/kubernetes/manifests directory
on the control plane node. kubelet watches this location and brings up the control plane.
If you observe the IPs of these control plane pods, they share the node IP. Because, they are configured with host network. Because they need to start with the cluster.
This solves the famous chicken-and-egg problem is kubernetes. Ideally, the cluster's network plugin is responsible for assigning IPs to the pods from the cluster IP pool. During the cluster startup, if the control plane pods wait for the network plugin to assign IPs, they will be in pending state forever. Because the network plugin won't start unless the control plane pods are up.
CoreDNS
In the Kubernets cluster, CoreDNS enables pods to communicate with each other using their names.
This is also a control plane component running in the kube-system namespace as a service.
kubectl get service -n kube-system
PS D:\Learning\Kubernetes\CKA> kubectl get service -n kube-system NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE kube-dns ClusterIP 10.96.0.10 <none> 53/UDP,53/TCP,9153/TCP 82m
The component is CoreDNS but the deployed service name is kube-dns, notice that.
kube-proxy injects the CoreDNS IP 10.96.0.10 into the /etc/resolv.conf file
on all the pods and thus helps in resolving the pod names to IPs.