Kubernetes Pod Networking & CNI

How every Pod gets a unique routable IP via CNI plugins. Pod-to-Pod communication on the same node (via Linux bridge) and across nodes (via VXLAN/BGP). kube-proxy vs Cilium eBPF for Service IP routing.

Overview

How Pods get on the network

Every Pod in Kubernetes receives its own unique, routable IP address. This is the fundamental networking contract of the platform. Pod IPs are ephemeral, so Services provide the stable IP and DNS name that the rest of the cluster uses.

What CNI does

The Container Network Interface (CNI) is the plugin layer that implements this contract. When kubelet starts a new Pod, it calls the configured CNI plugin. The plugin allocates an IP from the pod CIDR and wires up the network namespace.

Same node vs cross node

  • Same node — Two Pods talk through the Linux virtual bridge, commonly named cbr0; the bridge acts like a virtual switch — No tunnel or encapsulation; packets travel at wire speed within the node
  • Cross node, VXLAN — The original Layer 3 packet is wrapped in a UDP outer header, carried over the underlay to Node 2 and decapsulated there — Encapsulation overhead
  • Cross node, Calico BGP — Skips encapsulation and programs real routes — Faster, but the underlay must support BGP peering

Service routing

kube-proxy runs on every node and watches the API server for Service and Endpoint objects. When a Service is created, kube-proxy writes iptables or IPVS rules that DNAT the stable ClusterIP to one of the healthy Pod IPs. Cilium in eBPF mode replaces kube-proxy entirely with faster kernel-level forwarding.

> [!IMPORTANT] Never hardcode a Pod IP: it changes on every restart or reschedule. Use the Service name.

CNI plugins to know

  • Flannel — VXLAN only — Simple, minimal features
  • Calico — BGP or VXLAN — Supports NetworkPolicy
  • Cilium — eBPF — Replaces kube-proxy, deep observability through Hubble

> [!WARNING] Flannel does not enforce NetworkPolicy; pick Calico or Cilium if the cluster needs policy.

Key concepts

CNI (Container Network Interface)
Plugin specification that Kubernetes uses to set up Pod networking. kubelet calls the CNI binary when a Pod starts; the plugin allocates an IP from the pod CIDR and creates the veth pair connecting the pod network namespace to the node bridge.
Pod CIDR
A non-overlapping IP range assigned to each node. All Pods on that node receive IPs within the node's pod CIDR. The cluster-wide pod CIDR is set at cluster creation (e.g., 10.244.0.0/16).
VXLAN encapsulation
Virtual Extensible LAN — wraps the original pod-to-pod Layer 3 packet inside a UDP outer header so it can traverse the physical network between nodes. The CNI agent on the destination node strips the outer header and delivers the original packet.
kube-proxy
Runs on every node and programs iptables/IPVS rules to DNAT Service ClusterIP traffic to actual pod IPs. Watches the API server and updates rules whenever Services or Endpoints change.
CoreDNS
The in-cluster DNS server. Resolves ..svc.cluster.local to the Service ClusterIP. Pods use CoreDNS as their default nameserver.
Pod IP is ephemeral — Service IP is stable
Core Kubernetes principle. Never hardcode Pod IPs in config or code. Always use the Service name or ClusterIP which remains constant across Pod restarts and rescheduling.

When to use it

  • Designing multi-node Kubernetes clusters and choosing a CNI plugin
  • Debugging pod-to-pod connectivity failures across nodes
  • Explaining why Service IPs are stable but Pod IPs are not
  • Interview questions about how Kubernetes networking is implemented at the kernel level
  • Evaluating kube-proxy vs eBPF-based forwarding for high-throughput workloads

Interview questions

  • How does a Pod get its IP address in Kubernetes?
  • Compare kube-proxy iptables mode vs Cilium eBPF mode.
  • What happens at the network level when Pod A on Node 1 sends a packet to Pod B on Node 2?

Sign up free to read the full topic

More DevOps topics

Start free on Cariara · Coding problems · System design studio