A Kubernetes cluster is divided into a control plane that makes global decisions and worker nodes that actually run workloads. The control plane runs the kube-apiserver as its front-end and the only component that talks directly to etcd, which is a distributed consistent key-value store using the Raft consensus algorithm that holds all cluster state, including node information, Pod specs, and Secrets. Because losing etcd data effectively destroys the cluster, regular backups are essential. The kube-scheduler watches for newly created Pods without an assigned node and chooses one based on resource fit, affinity rules, taints and tolerations, and topology spread constraints, while the kube-controller-manager runs core controller loops that reconcile actual state toward desired state for resources such as nodes, Jobs, endpoints, and ServiceAccount tokens.
Worker nodes run the kubelet, kube-proxy, and a container runtime. The kubelet is the node agent that registers the node with the apiserver, watches for Pod specs assigned to it, runs init containers in order, pulls images through the Container Runtime Interface, sets up networking via a CNI plugin, mounts volumes, starts containers, runs health probes with configurable delay parameters, and reports status back. kube-proxy maintains iptables, IPVS, or eBPF rules on each node so traffic destined for Service cluster IPs is load-balanced to the correct backend Pods. The container runtime, which is responsible for actually running containers, must implement the CRI; supported options include containerd, CRI-O, and Mirantis Container Runtime, with Docker no longer supported directly since Kubernetes v1.24 because it sits on top of containerd. Every Pod also runs a tiny pause container that holds the network namespace and serves as the parent of all other containers in the Pod, giving them their shared IP and volume mount points. Networking is delegated to CNI plugins such as Calico, Cilium, Flannel, and Weave Net, which assign Pod IPs and configure routes when each Pod starts, and the kubelet's own configuration in /var/lib/kubelet/config.yaml controls cluster DNS, image pull policy, and cgroup driver settings. The apiserver exposes its REST interface at https://<apiserver>:6443 by default, with OpenAPI specifications available at /openapi/v2 and /openapi/v3, reachable only through client certificates, bearer tokens, or OIDC authentication. Pods transition through Pending, Running, Succeeded, Failed, and Unknown phases based on the kubelet's lifecycle, and graceful shutdown sends SIGTERM followed by SIGKILL after terminationGracePeriodSeconds, optionally preceded by a preStop hook for cleanup logic.