Instalación y Configuración de CoreDNS
CoreDNS es un servidor DNS flexible y extensible escrito en Go, que sirve como el servidor DNS por defecto en Kubernetes y puede desplegarse como servidor DNS de propósito general en Linux. Su arquitectura basada en plugins permite componerlo para cualquier caso de uso: autoridad, resolución recursiva, caché, reenvío y descubrimiento de servicios. Esta guía cubre la instalación de CoreDNS, configuración de plugins, zonas personalizadas e integración con Kubernetes.
Requisitos Previos
- Servidor Linux (Ubuntu 22.04/Debian 12 o CentOS 9/Rocky 9)
- Mínimo 512 MB de RAM (1 GB recomendado)
- Puerto 53 disponible (no conflictos con systemd-resolved u otro DNS local)
- Acceso root al servidor
Instalación de CoreDNS
# Obtener la última versión de CoreDNS
COREDNS_VERSION="1.11.1"
# Descargar el binario precompilado
wget "https://github.com/coredns/coredns/releases/download/v${COREDNS_VERSION}/coredns_${COREDNS_VERSION}_linux_amd64.tgz"
tar xzf "coredns_${COREDNS_VERSION}_linux_amd64.tgz"
# Instalar el binario
install -m 755 coredns /usr/local/bin/coredns
# Verificar la instalación y los plugins incluidos
coredns --version
coredns -plugins
# Crear usuario de sistema para CoreDNS
useradd -r -d /etc/coredns -s /bin/false coredns
# Crear directorios de configuración
mkdir -p /etc/coredns /var/lib/coredns
chown coredns:coredns /var/lib/coredns
# Asignar capacidad para binding en puerto 53 sin root
setcap cap_net_bind_service=+ep /usr/local/bin/coredns
Configuración Básica con Corefile
El Corefile es el archivo de configuración principal de CoreDNS:
cat > /etc/coredns/Corefile << 'EOF'
# Servidor DNS principal - atiende todas las consultas en el puerto 53
. {
# Reenviar consultas no resueltas localmente a servidores upstream
forward . 1.1.1.1 8.8.8.8 {
protocol udp
max_concurrent 1000
}
# Caché de respuestas para mejorar el rendimiento
cache {
success 9984 300 # Cachear respuestas exitosas hasta 300 segundos
denial 9984 30 # Cachear respuestas NXDOMAIN 30 segundos
}
# Logs de errores (no loguear cada query para reducir I/O)
errors
# Métricas de Prometheus en el puerto 9153
prometheus :9153
# Health check endpoint en el puerto 8080
health :8080 {
lameduck 5s
}
# Listo para tráfico
ready :8181
}
EOF
chown coredns:coredns /etc/coredns/Corefile
Crea el servicio systemd:
cat > /etc/systemd/system/coredns.service << 'EOF'
[Unit]
Description=CoreDNS - DNS Server
Documentation=https://coredns.io
After=network-online.target
Wants=network-online.target
[Service]
Type=simple
User=coredns
Group=coredns
ExecStart=/usr/local/bin/coredns -conf /etc/coredns/Corefile
ExecReload=/bin/kill -SIGUSR1 $MAINPID
Restart=on-failure
RestartSec=5s
LimitNOFILE=1048576
LimitNPROC=512
[Install]
WantedBy=multi-user.target
EOF
# Deshabilitar systemd-resolved si está en el puerto 53
# (en Ubuntu, systemd-resolved ocupa el puerto 53 por defecto)
systemctl disable --now systemd-resolved
rm -f /etc/resolv.conf
echo "nameserver 127.0.0.1" > /etc/resolv.conf
systemctl daemon-reload
systemctl enable --now coredns
# Probar la resolución DNS
dig @127.0.0.1 google.com
dig @127.0.0.1 google.com AAAA
Plugin de Caché
Optimiza la caché de CoreDNS para alto rendimiento:
cat > /etc/coredns/Corefile << 'EOF'
. {
forward . 1.1.1.1 1.0.0.1 8.8.8.8 8.8.4.4 {
policy round_robin
health_check 5s
}
# Caché optimizada para producción
cache {
success 10000 600 300 # max_items ttl min_ttl
denial 5000 30 5 # max_items ttl min_ttl
prefetch 10 1m 10% # Precarga proactiva al llegar al 10% del TTL
}
errors
prometheus :9153
health :8080
}
EOF
Reenvío de Consultas
Configura reenvío selectivo por dominio:
cat > /etc/coredns/Corefile << 'EOF'
# Dominio interno de la empresa - resolver con servidor interno
empresa.local {
forward . 10.0.0.10 10.0.0.11
cache 60
errors
}
# Consultas para Kubernetes - resolver con kube-dns
cluster.local {
forward . 10.96.0.10
cache 30
}
# Todo lo demás - reenviar a DNS público con DoT
. {
forward . tls://1.1.1.1 tls://1.0.0.1 {
tls_servername cloudflare-dns.com
health_check 5s
}
cache {
success 9984 300
denial 9984 30
}
errors
prometheus :9153
health :8080
}
EOF
# Recargar configuración sin reiniciar el servicio
systemctl reload coredns
# o enviar señal al proceso
kill -SIGUSR1 $(pgrep coredns)
Gestión de Zonas
Configura CoreDNS como servidor autoritativo para una zona:
# Crear archivo de zona en formato RFC 1035
cat > /etc/coredns/zones/db.empresa.local << 'EOF'
$ORIGIN empresa.local.
$TTL 300
@ IN SOA ns1.empresa.local. admin.empresa.local. (
2024011501 ; Serial (YYYYMMDDNN)
3600 ; Refresh
900 ; Retry
604800 ; Expire
300 ) ; Minimum TTL
; Servidores de nombres
@ IN NS ns1.empresa.local.
@ IN NS ns2.empresa.local.
; Registros A del propio servidor NS
ns1 IN A 10.0.0.10
ns2 IN A 10.0.0.11
; Registros de la infraestructura
web IN A 10.0.1.10
web IN A 10.0.1.11
api IN A 10.0.2.10
db IN A 10.0.3.10
mail IN A 10.0.4.10
mail IN MX 10 mail.empresa.local.
; Alias CNAME
www IN CNAME web.empresa.local.
app IN CNAME api.empresa.local.
EOF
# Añadir el bloque de zona al Corefile
cat >> /etc/coredns/Corefile << 'EOF'
# Zona autoritativa para empresa.local
empresa.local {
file /etc/coredns/zones/db.empresa.local {
reload 10s # Recargar el archivo si cambia
}
errors
log
}
EOF
# Verificar la configuración
coredns -conf /etc/coredns/Corefile -dns.port 5300 &
dig @127.0.0.1 -p 5300 web.empresa.local
dig @127.0.0.1 -p 5300 empresa.local MX
kill %1
Integración con Kubernetes
En Kubernetes, CoreDNS se gestiona como un Deployment en el namespace kube-system:
# Ver la configuración actual de CoreDNS en Kubernetes
kubectl get configmap coredns -n kube-system -o yaml
# Editar la configuración de CoreDNS en Kubernetes
kubectl edit configmap coredns -n kube-system
# Corefile típico de Kubernetes
# .: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
# }
# Añadir reenvío para dominio interno al Corefile de Kubernetes
kubectl patch configmap coredns -n kube-system --patch '
data:
Corefile: |
empresa.local:53 {
forward . 10.0.0.10
}
.:53 {
errors
health
ready
kubernetes cluster.local in-addr.arpa ip6.arpa {
pods insecure
fallthrough in-addr.arpa ip6.arpa
ttl 30
}
forward . /etc/resolv.conf
cache 30
loop
reload
loadbalance
}
'
# Reiniciar CoreDNS para aplicar cambios
kubectl rollout restart deployment coredns -n kube-system
Políticas de Resolución Personalizadas
# Plugin "rewrite" para renombrar consultas DNS
cat >> /etc/coredns/Corefile << 'EOF'
# Redirigir consultas antiguas al nuevo dominio
old.empresa.com {
rewrite name suffix .old.empresa.com .empresa.local
forward . 127.0.0.1
}
EOF
# Plugin "hosts" para resolución estática (como /etc/hosts)
. {
hosts /etc/coredns/custom-hosts {
10.0.1.50 legacy-app.empresa.local
10.0.1.51 old-db.empresa.local
fallthrough
}
# ... resto de la configuración
}
Solución de Problemas
# Habilitar logging detallado de consultas (útil para depuración, no para producción)
# Añadir el plugin "log" al bloque deseado en el Corefile:
# . {
# log # Loguea cada consulta
# ...
# }
# Ver logs del servicio
journalctl -u coredns -f
# Probar resolución desde el servidor
dig @127.0.0.1 google.com
dig @127.0.0.1 empresa.local NS
dig @127.0.0.1 web.empresa.local
# Verificar que el puerto 53 está escuchando
ss -ulnp | grep 53
# Validar el Corefile antes de recargar
coredns -conf /etc/coredns/Corefile -validate
# Ver métricas en tiempo real
curl -s http://localhost:9153/metrics | grep coredns_cache
# Comprobar el health check
curl http://localhost:8080/health
curl http://localhost:8181/ready
Conclusión
CoreDNS ofrece una solución DNS moderna y extremadamente flexible gracias a su arquitectura de plugins, que permite construir desde un simple forwarder con caché hasta un servidor autoritativo completo con integración Kubernetes. Su diseño eficiente en Go y el soporte nativo de métricas Prometheus lo hacen ideal tanto para entornos de contenedores como para infraestructuras Linux tradicionales.


