Kubernetes Internal DNS
kubernetes dns is for service objects. DNS is served as a pod in the cluster.
Set up kubelet to use DNS
Modify kubelet definition file(/etc/kubernetes/kubelet) on all minions. Add the following options.
--cluster-dns=<DNS service ip> (should be one of clusterIP range)
--cluster-domain=<default local domain>
ex)
--cluster-dns=10.24.0.10
--cluster-domain=kubic.local
Restart kubelet service on all minions
$ sudo systemctl daemon-reload
$ sudo systemctl restart kubelet
Run kubedns pod and service
Create manifest files for DNS
- Service manifest file (conffiles/kube-system/kubedns/svc_kubedns.yml)
- Deployment manifest file (conffiles/kube-system/kubedns/dep_kubedns.yml)
These manifest files are based on https://github.com/kubernetes/kubernetes/tree/master/cluster/addons/dns
Note) If the cluster is not TLS enabled, you have to specify kubemaster in args of kubedns container. (–kube-master-url=http://:8080) If the cluster is working with TLS, there is no need to modify.
Run each manifest file.
$ kubectl create -f svc_kubedns.yml
$ kubectl create -f dep_kubedns.yml
Check if deployment, pods, and service are up okay.
$ kubectl get deploy -n kube-system
NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE
kube-dns 1 1 1 1 28m
$ kubectl get po -n kube-system
NAME READY STATUS RESTARTS AGE
kube-dns-3246654209-znk45 3/3 Running 0 28m
$ kubectl get svc -n kube-system
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kube-dns 10.24.0.10 <none> 53/UDP,53/TCP 4d
There are 3 containers running in a pod(kube-dns-3246654209-znk45)
* kubedns: dns service listening on port 10053(udp/tcp) and 10055(tcp)
* dnsmasq: dns proxy service listening on port 53(udp/tcp)
* sidecar: health check service listening on 10054(tcp)
Test DNS Service
Check if DNS is working inside a container. any service will have dns name with the following order.
<service_name>.<namespace>.svc.<cluster_domain>
ex) kubernetes.default.svc.kubic.local
Kubernetes apiserver service name is ‘kubernetes’ and it runs in ‘default’ namespace. So its fqdn(fully qualified domain name) will be kubernetes.default.svc.kubic.local.
I’ll use busybox(conffiles/myfiles/dep_busybox.yml)
$ kubectl create -f dep_busybox.yml
$ kubectl exec -it busybox sh
/# nslookup kubernetes
Server: 10.24.0.10
Address 1: 10.24.0.10 kube-dns.kube-system.svc.kubic.local
Name: kubernetes
name with the following order.
<service_name>.<namespace>.svc.<cluster_domain>
ex) kubernetes.default.svc.kubic.local
Kubernetes apiserver service name is ‘kubernetes’ and it runs in ‘default’ namespace. So its fqdn(fully qualified domain name) will be kubernetes.default.svc.kubic.local.
I’ll use busybox(conffiles/myfiles/dep_busybox.yml)
$ kubectl create -f dep_busybox.yml
$ kubectl exec -it busybox sh
/# nslookup kubernetes
Server: 10.24.0.10
Address 1: 10.24.0.10 kube-dns.kube-system.svc.kubic.local
Name: kubernetes
kubernetes.default.svc.kubic.local.
I’ll use busybox(conffiles/myfiles/dep_busybox.yml)
$ kubectl create -f dep_busybox.yml
$ kubectl exec -it busybox sh
/# nslookup kubernetes
Server: 10.24.0.10
Address 1: 10.24.0.10 kube-dns.kube-system.svc.kubic.local
Name: kubernetes
Address 1: 10.24.0.1 kubernetes.default.svc.kubic.local
We can see it automatically refer to the internal kubedns and kubedns gives the IP for kubernetes hostname. One curious thing is I put only ‘kubernetes’ but it is expanded to ‘.default.svc.kubic.local’. The magic is in /etc/resolv.conf.
If you see /etc/resolv.conf in the container, it shows:
search default.svc.kubic.local svc.kubic.local kubic.local
nameserver 10.24.0.10
options ndots:5
Look at ‘options ndots:5’. That makes resolver expands kubernetes to kubernetes.default.svc.kubic.local. kubernetes.default and kubernetes.default.svc will also be expaneded.