[ตอนที่ 4] Deploy NodelocalDNS มาช่วย CoreDNS /Kube-dns

Thanaphat Nuangjumnong
3 min readJun 19, 2020

NodeLocal DNSCache ปรับปรุงประสิทธิภาพของ DNS Cluster โดยการเรียกใช้งาน Cache dns on Cluster node เป็น DaemonSet ทุกวันนี้ Pods ใช้งาน ClusterFirst DNS mode จะเข้าถึงบริการ kube-dns IP สำหรับการค้นหา DNS queries สิ่งนี้ถูกแปลเป็นปลายทาง kube-dns / CoreDNS โดยผ่าน iptables ที่เพิ่มเข้าไปโดย kube-proxy ดังนั้นด้วยสถาปัตยกรรมใหม่นี้ Pods จะเข้าถึง dns caching agent ที่ทำงานบน Node เดียวกันดังนั้นจึงหลีกเลี่ยง iptables DNAT rules and connection tracking. หน้าที่สำหรับ caching agent ค้นหาแคชที่หายไปของชื่อโฮสต์ของคลัสเตอร์ (cluster.local suffix by default) อ่านต่อที่

## ทำไมทางทีมเราถึงเลือก nodelocaldns

  1. Pod ที่มี DNS QPS สูงสุดต้องติดต่อกับโหนดอื่นหากไม่มี kube-dns / CoreDNS ดังนั้นการจำเป็นต้องมี Local cache มาช่วยเรื่อง latency time
  2. ข้าม iptables DNAT และการติดตามการเชื่อมต่อจะช่วยลดการแข่งขัน conntrack และหลีกเลี่ยงรายการ UDP DNS ที่เติมตาราง conntrack
  3. การเชื่อมต่อจาก local caching agent ไปยัง kube-dns service สามารถอัพเกรดเป็น TCP การทำงานของ TCP conntrack จะถูกลบเมื่อการเชื่อมต่อใกล้เคียงกับ UDP ที่หมดเวลา (ค่าเริ่มต้น nf_conntrack_udp_timeout คือ 30 วินาที)
  4. อัพเกรด DNS queries from UDP to TCP เนื่องจากแพ็คเก็ต UDP ที่ลดลงและการหมดเวลา DNS มักจะสูงถึง 30 วินาที (3 retries + 10s timeout)
  5. มี Metrics สามารถมองเห็น dns requests ในระดับ Node
  6. Negative caching สามารถเปิดใช้งานได้อีกครั้งซึ่งช่วยลดจำนวนการค้นหาไปยังบริการ kube-dns service.
https://kubernetes.io/docs/tasks/administer-cluster/nodelocaldns/

## Download Source file

wget https://raw.githubusercontent.com/kubernetes/kubernetes/master/cluster/addons/dns/nodelocaldns/nodelocaldns.yaml

##Get IP kube-dns

kubectl get svc kube-dns -n kube-system -o jsonpath={.spec.clusterIP}

##Get dnsDomain

kubectl get cm -n kube-system kubeadm-config -o yaml |grep dnsDomain

## Note variables in the manifest with the right values:

kubedns=10.233.0.10
domain=cluster.local
localdns=169.254.20.10 ## (169.254.20.10 by default).

## If kube-proxy is running in IPVS mode:

**Default Template

sed -i "s/__PILLAR__LOCAL__DNS__/$localdns/g; s/__PILLAR__DNS__DOMAIN__/$domain/g; s/__PILLAR__DNS__SERVER__//g; s/__PILLAR__CLUSTER__DNS__/$kubedns/g" nodelocaldns.yaml

## Run cmd Custom Template

sed -i "s/__PILLAR__LOCAL__DNS__/169.254.20.10/g; s/__PILLAR__DNS__DOMAIN__/cluster.local/g; s/__PILLAR__DNS__SERVER__//g; s/__PILLAR__CLUSTER__DNS__/10.233.0.10/g" nodelocaldns.yaml

## Re-check nodelocaldns.yaml has error syntex

vi nodelocaldns.yaml
**solve by remove ,

## Deployment

kubectl create -f nodelocaldns.yaml
kubectl get pod -n kube-system

## Edit kubelet config (All Master / Work node)

อธิบายเพิ่มเติม เนื่องจาก Kubelet config ของทุกๆ Server (Master /Node) จะมี Parameter ชื่อ clusterDNS ชี้ไปยัง Service สำหรับการค้นหา DNS querie (kube-dns by default) เราจะแก้ไขให้ชี้ที่ 169.254.25.10 (IP Dummy Nodelocaldns)

10.233.0.10 == IP Service kube-dns

## edit kubelet config

vi /var/lib/kubelet/config.yaml

clusterDNS:- 10.233.0.10 >>> 169.254.20.10

## Restart kubelet service

systemctl daemon-reload
systemctl restart kubelet

## How to checking /etc/resolv.conf
## **Focus >> nameserver 169.254.25.10 (IP Dummy Nodelocaldns)

kubectl exec -ti nginx-76df748b9-r48lg — cat /etc/resolv.conf

PS. ถ้า Namesever ยังไม่เปลี่ยนจาก 10.233.0.10 >>> 169.254.20.10 แนะนำให้ Restart pod ก่อนนะครับ

ขอบคุณแหล่งเนื้อหาที่อ้างอิงครับ

https://kubernetes.io/docs/tasks/administer-cluster/nodelocaldns/
https://github.com/kubernetes/kubernetes/tree/master/cluster/addons/dns/nodelocaldns
https://github.com/kubernetes/kubernetes/issues/56903

--

--