Full lesson
Explore the full explanation, examples, and visuals at your own pace.
orders calls http://payments
DNS turns the name payments into a Service IP, and the Service forwards to one Pod. Here, the orders Pod asks CoreDNS to look up payments, sends its request to that IP, and the payments Service passes it to either Pod A or Pod B.
Step 1: name to IP
The orders Pod's DNS settings point at CoreDNS, and include a search list. So the short name payments gets expanded to payments.shop.svc.cluster.local. The Pod asks CoreDNS to resolve it, and CoreDNS replies with the Service's ClusterIP, 10.96.0.15. That's the whole job of this step.
A ClusterIP is a stable virtual address, not a machine.
No Pod owns 10.96.0.15. It's a stable virtual address that stays fixed, even while the Pods behind it come and go.
Step 2: which Pods are behind it?
The payments Service carries the selector app=payments, so Kubernetes finds Pods with that label. Pod A and Pod B match, and their ready IPs, 10.244.1.7 and 10.244.2.9, get written into the EndpointSlice. Service port 80 maps to targetPort 8080 on those Pods.
Step 3: the packet reaches a Pod
The orders Pod sends its request to 10.96.0.15 on port 80. kube-proxy has programmed rules on every node, so the sender's own node rewrites that destination to one endpoint, here Pod A at 10.244.1.7 on port 8080. Some clusters use eBPF instead, but the effect is the same.
The payments Service selector is app equals payment, but the Pods are labeled app equals payments. What happens when orders calls payments?
The payments Service selector is app equals payment, but the Pods are labeled app equals payments. What happens when orders calls payments?
- DNS fails to resolve the name payments
- DNS resolves, but no Pod receives the request
- Kubernetes sends it to any Pod in the namespace
The payments Service selector is app equals payment, but the Pods are labeled app equals payments. What happens when orders calls payments?
DNS resolves, but no Pod receives the request. DNS only knows the Service exists, so it still returns the ClusterIP. But the selector matches no Pods, so the EndpointSlice is empty and the node rules have nowhere to forward. Kubernetes never guesses a Pod.
- DNS fails to resolve the name payments
- DNS resolves, but no Pod receives the request
- Kubernetes sends it to any Pod in the namespace
Pod B fails readiness; Pod C joins
Pod B fails readiness, so the EndpointSlice removes it. Pod C becomes ready and joins. The payments Service just reads the updated list. Orders still calls payments, and the name and ClusterIP never change. Only the set of ready backends behind them moves.
When the call fails, check
Debug by stage. If the name fails, DNS lookup is the problem, so check the Service name and namespace. If it resolves but hangs, the selector matched no Pods. Across namespaces, use payments dot othernamespace.
- Name fails: wrong namespace or Service name
- Resolves, no reply: selector matches no Pods
- Other namespace: use payments.othernamespace
Name, then Service IP, then a ready Pod
DNS gives a stable Service address; node rules pick a Pod. So payments resolves to 10.96.0.15, and from that virtual IP, the rules on the node send your request to a ready backend, like Pod A.




