Cloud/Kubernetes

CoreDNS

Jinseung's Blog 2026. 9. 9. 20:22

이번 블로그에서는 Kubernetes의 기본 DNS 서버인 CoreDNS의 개념에 대한 글을 작성해보겠습니다.

CoreDNS 개념

CoreDNS는 Kubernetes 클러스터의 기본 DNS 서버로, Service, Pod 이름을 클러스터 내부 IP로 변환(서비스 디스커버리)하고 클러스터 외부 도메인 질의는 상위(upstream) DNS로 포워딩하는 모듈형 DNS 애플리케이션입니다.

 

위치와 역할

  • Kubernetes 1.13부터 kube-dns를 대체한 기본 클러스터 DNS 
  • kube-system 네임스페이스에 Deployment로 실행되고, 그 앞에 kube-dns라는 이름의 Service(ClusterIP)가 붙습니다. ( Service 이름이 kube-dns인 이유는 과거 호환성 때문입니다.)
  • 클러스터의 모든 Pod는 이 DNS Service IP를 /etc/resolv.conf의 nameserver로 받아 사용합니다.

DNS 이름 규칙

  • Service : <service-name>.<namespace>.svc.cluster.local
    • 같은 네임스페이스면 <service-name> 만으로도 조회 가능합니다.
    • Headless Service(clusterIP: None)는 A 레코드가 각 Pod IP로 반환됩니다.
    • SRV 레코드로 포트 정보도 조회 가능: _<port-name>._<protocol>.<service>.<ns>.svc.cluster.local
  • Pod : 기본은 IP 기반입니다. 10-244-1-5.<namespace>.pod.cluster.local 형태 (IP의 .을 -로 치환)

resolv.conf와 ndots

Pod 안 /etc/resolv.conf는 대략 이렇게 세팅되게 됩니다.

nameserver 10.96.0.10          # kube-dns Service IP
search <ns>.svc.cluster.local svc.cluster.local cluster.local
options ndots:5

 

ndots:5: 조회하려는 이름에 점(.)이 5개 미만이면 먼저 search 도메인들을 붙여서 순서대로 질의합니다. 그래서 google.com(점 1개) 같은 외부 도메인도 google.com.<ns>.svc.cluster.local 등을 먼저 시도해 불필요한 질의가 여러 번 발생할 수 있습니다 → DNS 성능 이슈의 흔한 원인이기도 합니다.

 

Corefile 설정 파일

CoreDNS는 플러그인 체인으로 동작하며, kube-system의 coredns ConfigMap에 담긴 Corefile로 설정합니다.

.:53 {
    errors
    health {
        lameduck 5s
    }
    ready
    kubernetes cluster.local in-addr.arpa ip6.arpa {
        pods insecure
        fallthrough in-addr.arpa ip6.arpa
        ttl 30
    }
    prometheus :9153
    forward . /etc/resolv.conf {
        max_concurrent 1000
    }
    cache 30
    loop
    reload
    loadbalance
}

 

  • .:53 : 모든 존(.)을 53 포트에서 처리한다는 서버 블록
  • 위에서 아래로 플러그인이 체인처럼 엮여 질의를 처리

주요 플러그인

kubernetes 클러스터 도메인(cluster.local)의 Service/Pod 질의를 API 서버 정보로 응답. pods insecure/verified/disabled 옵션
forward 클러스터 도메인이 아닌 질의를 상위 DNS(기본 /etc/resolv.conf, 즉 노드 DNS)로 전달
cache 응답 캐싱(기본 TTL 30초)으로 상위 질의 부하 감소
errors 에러를 stdout으로 로깅
health :8080/health 헬스 엔드포인트 (livenessProbe용). lameduck은 종료 전 유예 시간
ready :8181 준비 상태(200 OK) 반환 (readinessProbe용)
prometheus :9153/metrics로 메트릭 노출
loop DNS 포워딩 루프 감지 시 프로세스 종료로 무한루프 방지
reload Corefile 변경을 재시작 없이 자동 반영(약 2분 지연)
loadbalance A/AAAA 레코드 순서를 라운드로빈으로 섞어 부하 분산
fallthrough 해당 플러그인이 처리 못한 질의를 다음 플러그인으로 넘김

 

관련 명령어

CoreDNS 리소스 확인 명령어

kubectl get deployment coredns -n kube-system
kubectl get svc kube-dns -n kube-system
kubectl get configmap coredns -n kube-system -o yaml
kubectl -n kube-system logs -l k8s-app=kube-dns

 

 

Pod 내부에서 DNS 해석 테스트

# 임시 디버그 Pod
kubectl run -it --rm dnsutils --image=registry.k8s.io/e2e-test-images/agnhost:2.39 -- sh

# 안에서
nslookup kubernetes.default            # ClusterIP 반환되면 정상
nslookup my-svc.my-namespace.svc.cluster.local
cat /etc/resolv.conf                   # nameserver / search / ndots 확인

커스텀 스텁 도메인 추가 방법

consul.local 질의는 별도 DNS(10.150.0.1)로 보내고, 나머지 외부 질의는 특정 nameserver(172.16.0.1)로 포워딩 합니다.

.:53 {
    errors
    health
    kubernetes cluster.local in-addr.arpa ip6.arpa {
        pods insecure
        fallthrough in-addr.arpa ip6.arpa
    }
    prometheus :9153
    forward . 172.16.0.1
    cache 30
    loop
    reload
    loadbalance
}
consul.local:53 {
    errors
    cache 30
    forward . 10.150.0.1
}

 

이것으로 Kubernetes의 기본 DNS 서버인 CoreDNS에 대한 글을 마치겠습니다. 감사합니다!

 

'Cloud > Kubernetes' 카테고리의 다른 글

EKS S3 CSI Driver  (0) 2026.07.09
Calico CNI  (0) 2026.01.05
NodeLocal DNSCache  (0) 2025.10.27
Istio Keycloak 인증 연동  (0) 2025.09.29
쿠버네티스 기본 명령어를 알아보자  (0) 2025.05.01