KubernetesCXXII · DNS TroubleshootingDNS troubleshooting
External DNS and split-horizon — the cluster to enterprise DNS
What you'll learn
- Reason about External DNS and split-horizon DNS
- Publish cluster Services to the enterprise DNS
- Diagnose DNS failures between the cluster and the enterprise
- Identify the production failure modes of split-horizon DNS
Prerequisites
Verified against Kubernetes 1.34.x · kubeadm 1.34.x · kubectl 1.34.x · etcd 3.6.x · CoreDNS 1.11.x · containerd 1.7.x / 2.x · 2026-08-16
Nothing inside the cluster notices when external DNS records go stale. The Service is healthy, the load balancer holds an address, and the only symptom is that clients outside the cluster still resolve last week’s IP, because the external-dns controller’s provider credentials expired or its API calls are being rate-limited. Split-horizon makes that harder to catch: internal and external clients are answered differently by design, so resolving the name from inside a Pod proves nothing about what the outside world sees.
The external-dns controller
The external-dns controller is a Deployment that watches the cluster’s Services and Ingresses, and publishes the DNS records to the enterprise DNS provider (e.g., Route53, Cloud DNS, Azure DNS).
flowchart LR
A[Service/Ingress] --> B[external-dns controller]
B --> C[DNS provider API]
C --> D[Enterprise DNS]
D --> E[External clients]
The external-dns controller is the cluster’s DNS publication.
The DNS annotations
The external-dns controller uses the Service’s annotations to determine the DNS records to publish:
apiVersion: v1
kind: Service
metadata:
name: billing
namespace: prod
annotations:
external-dns.alpha.kubernetes.io/hostname: billing.example.com
external-dns.alpha.kubernetes.io/ttl: "300"
spec:
type: LoadBalancer
...
The annotations are the cluster’s DNS configuration.
The split-horizon DNS
The split-horizon DNS is a DNS configuration that returns different answers based on the client’s network. The cluster-internal clients get the ClusterIP; the external clients get the cloud LB’s IP.
flowchart TD
A[Client query: billing.example.com] --> B{Client network?}
B -->|Internal| C[Cluster-IP: 10.96.45.123]
B -->|External| D[LoadBalancer IP: 1.2.3.4]
The split-horizon is the cluster’s DNS view.
The diagnostic
The canonical diagnostic:
# Substitute your own value before running: a pod in the cluster to run the
# lookup from.
SOURCE_POD=checkout-api-5f9c7d8b6c-2xk9p
# 1. Check the external-dns controller
kubectl get pods -n kube-system -l app=external-dns
# 2. Check the external-dns logs
kubectl logs -n kube-system -l app=external-dns --tail=200
# 3. Check the Service's annotations
kubectl get service billing -n prod -o yaml | grep -A5 annotations
# 4. Test the DNS from inside the cluster
kubectl exec -it "$SOURCE_POD" -- nslookup billing.prod.svc.cluster.local
# 5. Test the DNS from outside the cluster
nslookup billing.example.com
The diagnostic is the external-dns controller, the annotations, and the tests.
Common failures
- external-dns controller failing. The controller is not publishing the records. The remediation is to restart the controller.
- DNS provider authentication failing. The controller’s credentials are not valid. The remediation is to update the credentials.
- DNS provider rate limiting. The controller is exceeding the provider’s API rate limit. The remediation is to reduce the publish rate.
- Split-horizon misconfiguration. The internal and external clients are getting the wrong DNS records.
# Restart the external-dns controller
kubectl rollout restart deployment/external-dns -n kube-system
# Check the controller's logs for DNS provider errors
kubectl logs -n kube-system -l app=external-dns --tail=200 | grep -i "error"
The remediation
The remediation depends on the cause:
# Option 1: Restart the external-dns controller
kubectl rollout restart deployment/external-dns -n kube-system
# Option 2: Update the credentials
kubectl edit secret external-dns-credentials -n kube-system
# Option 3: Reduce the publish rate
kubectl edit deployment/external-dns -n kube-system
# Change --interval to a higher value
# Option 4: Fix the split-horizon
# (DNS provider-specific configuration)
The remediation is the DNS integration recovery.
Production discipline
External DNS is the cluster’s hypothesis. The discipline is to walk the canonical flow extended with the DNS integration, identify the failure mode, apply the remediation. The DNS is the cluster’s name resolution; the integration is the bridge.
- Check the external-dns controller. The controller is the cluster’s DNS publication.
- Check the credentials. The credentials are the controller’s authentication.
- Check the DNS provider. The provider is the cluster’s DNS destination.
Quiz
Knowledge check · 4 questions
Q1. What is the role of the external-dns controller?
Q2. A split-horizon DNS returns different answers based on the client's network.
Q3. A public DNS record still points at a decommissioned load balancer. Diagnose the external-dns failure and republish the record.
The billing Service in prod was recreated on Tuesday and now holds EXTERNAL-IP 203.0.113.44. From outside the cluster, billing.example.com still answers 203.0.113.12 forty minutes later, although the record's TTL is 300. In-cluster resolution of billing.prod.svc.cluster.local is correct.
Q4. Name three common causes of an external-dns failure and the diagnostic command for each.
Passing score: 75%. Answers are checked in this browser.