O DNS é um service de infraestrutura crítico do Kubernetes. Configurações incorretas no cliente e clusters em larga escala podem causar timeouts e falhas de resolução. Otimize a configuração do cliente e do servidor aplicando estas práticas recomendadas.
Observações de uso
Não se aplica a clusters CoreDNS gerenciados nem a clusters ACK com Auto Mode ativado. O CoreDNS gerenciado escala automaticamente com a carga de trabalho, tornando ajustes manuais desnecessários.
Conteúdo
As práticas recomendadas de DNS abrangem o lado do cliente e o lado do servidor:
-
No lado do cliente, reduza a latência de resolução otimizando as requisições de resolução de nomes de domínio. Minimize anomalias de resolução com imagens de container adequadas, sistemas operacionais de nó apropriados e NodeLocal DNSCache.
-
No lado do servidor CoreDNS, monitore o status de execução para detectar anomalias de DNS e identificar as causas raiz. Melhore a alta disponibilidade e o throughput de queries por segundo (QPS) do CoreDNS ajustando as configurações de implantação.
Consulte a documentação oficial do CoreDNS.
Otimize requisições de resolução de nomes de domínio
A resolução DNS é uma das atividades de rede mais frequentes no Kubernetes. Diversas requisições podem ser otimizadas ou evitadas:
(Recomendado) Utilize pools de conexão. Quando uma aplicação containerizada acessa outro service com frequência, mantenha as conexões upstream em cache na memória para evitar a resolução DNS e o estabelecimento de conexões TCP a cada acesso.
Utilize polling assíncrono ou long polling para obter o endereço IP de um nome de domínio DNS.
-
Utilize cache de DNS:
(Recomendado) Caso sua aplicação não suporte pools de conexão, armazene em cache os resultados da resolução DNS no lado da aplicação ou use NodeLocal DNSCache.
Se o NodeLocal DNSCache não estiver disponível, faça cache de consultas DNS dentro do container com o Name Service Cache Daemon (NSCD). Consulte Use NSCD in Kubernetes clusters.
Otimize o arquivo resolv.conf: os parâmetros ndots e search afetam a eficiência da resolução de acordo com a forma como você escreve os nomes de domínio nas configurações do container. Consulte DNS policy configuration and domain name resolution para mais detalhes sobre ndots e search.
-
Otimize a configuração de nomes de domínio para minimizar tentativas de resolução e reduzir o tempo de resolução:
Para acessar um Service no mesmo namespace, utilize
<service-name>, ondeservice-nameé o nome do Service.Para acessar um Service em outro namespace, utilize
<service-name>.<namespace-name>, ondenamespace-nameé o namespace do Service.-
Para domínios externos, utilize FQDNs (fully qualified domain names). Adicione um ponto final (.) ao nome para especificar endereços absolutos e evitar concatenações inválidas com o domínio
search. Por exemplo, use www.aliyun.com. em vez de www.aliyun.com.-
Em clusters na versão 1.33 ou posterior, defina o domínio de pesquisa como "." (consulte 125883) para obter um efeito semelhante:
dnsPolicy: None dnsConfig: nameservers: ["192.168.0.10"] ## Replace 192.168.0.10 with the actual CoreDNS service clusterIP searches: - . - default.svc.cluster.local ## Replace "default" with your namespace name - svc.cluster.local - cluster.localApós aplicar essa configuração, o arquivo /etc/resolv.conf no pod terá o seguinte conteúdo:
search . default.svc.cluster.local svc.cluster.local cluster.local nameserver 192.168.0.10O "." como primeiro domínio de pesquisa faz com que todas as requisições de domínio sejam tratadas como FQDNs e resolvidas diretamente, sem tentativas de busca desnecessárias.
ImportanteDefina
dnsPolicycomoNonepara que essa configuração tenha efeito.
-
Entenda a configuração DNS em containers
Diferentes resolvedores DNS podem apresentar comportamentos distintos. É possível que
dig <domain>funcione corretamente enquantoping <domain>falhe.-
Evite imagens base Alpine. Prefira outras imagens base, como Debian ou CentOS. A musl libc do Alpine difere da glibc e pode causar os seguintes problemas:
O Alpine 3.18 e versões anteriores não suportam fallback para TCP em consultas DNS.
O Alpine 3.3 e versões anteriores não suportam o parâmetro search nem domínios de pesquisa, o que bloqueia a descoberta de services.
Consultas simultâneas a múltiplos servidores DNS em /etc/resolv.conf podem invalidar as otimizações do NodeLocal DNSCache.
Consultas A e AAAA simultâneas no mesmo socket podem acionar conflitos de porta source no conntrack em kernels mais antigos, causando perda de pacotes.
Consulte musl libc.
Para aplicações Go, compreenda as diferenças entre as implementações do resolvedor DNS CGO e Pure Go.
Evite timeouts probabilísticos de resolução DNS causados por defeitos do IPVS
Com o IPVS como modo de balanceamento de carga do kube-proxy, é possível encontrar timeouts intermitentes de resolução DNS durante o scale-in ou reinicialização do CoreDNS devido a um defeito no kernel Linux. Consulte IPVS.
Reduza o impacto dos defeitos do IPVS utilizando um dos métodos a seguir:
Modifique o timeout de persistência de sessão UDP do IPVS no kube-proxy. Consulte How do I modify the IPVS UDP session persistence timeout in kube-proxy?.
Use o NodeLocal DNSCache
Em alguns cenários, o CoreDNS pode apresentar os seguintes problemas:
Consultas A e AAAA simultâneas podem, raramente, causar perda de pacotes e falhas de resolução DNS.
Tabelas conntrack cheias nos nós podem provocar perda de pacotes e falhas de resolução DNS.
Instale o add-on NodeLocal DNSCache para melhorar a estabilidade e o desempenho do DNS. Ele executa um cache DNS em cada nó. Consulte Use the NodeLocal DNSCache component para implantação em clusters ACK.
Após instalar o NodeLocal DNSCache, injete a configuração de cache DNS nos seus pods. Aplique um rótulo a um namespace para injetar automaticamente a configuração de cache DNS nos novos pods:
kubectl label namespace default node-local-dns-injection=enabled
Utilize uma versão adequada do CoreDNS
O CoreDNS mantém boa compatibilidade com versões anteriores do Kubernetes. Mantenha o CoreDNS em uma versão recente e estável. A página Component Management no console ACK oferece recursos de instalação, atualização e configuração. Monitore o status dos componentes e atualize o CoreDNS durante períodos de baixo tráfego quando uma atualização estiver disponível.
Consulte Automatic upgrade for non-managed CoreDNS para obter instruções de atualização.
Consulte as notas de versão em CoreDNS.
Versões do CoreDNS anteriores à v1.7.0 apresentam riscos conhecidos, incluindo, mas não se limitando a:
Se a conectividade entre o CoreDNS e o API server for interrompida durante uma reinicialização, migração ou instabilidade de rede, o CoreDNS poderá reiniciar por falha ao gravar logs de erro. Consulte Set klog's logtostderr flag.
O CoreDNS consome memória adicional durante a inicialização. O limite de memória padrão pode disparar problemas de out-of-memory (OOM) em clusters de grande porte, fazendo com que os pods do CoreDNS reiniciem repetidamente sem recuperação. Consulte CoreDNS uses a lot of memory during initialization phase.
O CoreDNS apresenta problemas conhecidos que afetam domínios de Headless Service e a resolução de domínios externos. Consulte plugin/kubernetes: handle tombstones in default processor e Data is not synced when CoreDNS reconnects to kubernetes api server after protracted disconnection.
Quando um nó está com problemas, versões desatualizadas do CoreDNS podem implantar pods nesse nó em razão das políticas de tolerância padrão. Esses pods podem não ser removidos automaticamente, ocasionando falhas na resolução de domínios.
A versão mínima recomendada do CoreDNS depende da versão do cluster Kubernetes:
|
Versão do cluster |
Versão mínima recomendada do CoreDNS |
|
Abaixo de 1.14.8 |
v1.6.2 (sem manutenção) |
|
1.14.8 e posteriores, abaixo de 1.20.4 |
v1.7.0.0-f59c03d-aliyun |
|
1.20.4 e posteriores, abaixo de 1.21.0 |
v1.8.4.1-3a376cc-aliyun |
|
1.21.0 e posteriores |
v1.11.3.2-f57ea7ed6-aliyun |
Monitorar o status de runtime do CoreDNS
Métricas de monitoramento
O CoreDNS expõe métricas de integridade, como resultados de resolução, por meio de uma interface Prometheus padrão para ajudar a detectar anomalias no CoreDNS ou nos servidores DNS upstream.
Prometheus for ACK inclui métricas de monitoramento e regras de alerta integradas para o CoreDNS. Ative o Prometheus e o Dashboard no Container Service for Kubernetes console. Consulte CoreDNS component monitoring.
Com uma instância Prometheus autogerenciada, observe as métricas relevantes e configure alertas para as críticas. Consulte a documentação oficial do CoreDNS para Prometheus.
Logs operacionais
Utilize os logs do CoreDNS para diagnosticar causas raiz quando ocorrerem anomalias de DNS. Ative os logs de resolução de domínio e a coleta de logs do SLS. Consulte Analyze and monitor CoreDNS logs.
Entrega de eventos do Kubernetes
No CoreDNS v1.9.3.6-32932850-aliyun e versões posteriores, ative o plugin k8s_event para entregar logs críticos do CoreDNS como eventos do Kubernetes ao Event Hub. Consulte a documentação do plugin k8s_event.
Instâncias do CoreDNS recém-implantadas têm esse recurso ativado por padrão. Ao atualizar a partir de uma versão anterior, modifique manualmente o arquivo de configuração para ativá-lo.
-
Abra o arquivo de configuração do CoreDNS:
kubectl -n kube-system edit configmap/coredns -
Adicione os plugins kubeAPI e k8s_event.
apiVersion: v1 data: Corefile: | .:53 { errors health { lameduck 15s } // Begin addition (ignore other differences). kubeapi k8s_event { level info error warning // Deliver critical logs with info, error, or warning levels. } // End addition. kubernetes cluster.local in-addr.arpa ip6.arpa { pods verified fallthrough in-addr.arpa ip6.arpa } // Omitted below. } Verifique o status e os logs do pod do CoreDNS. Se os logs contiverem a palavra
reload, a modificação foi realizada com sucesso.
Garantir alta disponibilidade do CoreDNS
O CoreDNS é o DNS autoritativo do cluster. Uma falha no CoreDNS pode interromper o acesso interno ao service e afetar grande parte do seu negócio. Garanta alta disponibilidade do CoreDNS com as seguintes medidas:
Avaliar a pressão sobre o componente CoreDNS
Execute testes de carga de DNS para avaliar a pressão sobre o add-on CoreDNS. Ferramentas open-source como DNSPerf podem ajudar. Se não for possível avaliar com precisão a pressão de DNS, siga estas recomendações:
Implante pelo menos dois pods do CoreDNS, cada um com limites de recursos de no mínimo 1 núcleo de CPU e 1 GB de memória.
A capacidade de QPS do CoreDNS está correlacionada ao uso de CPU. Com o NodeLocal DNSCache, cada núcleo de CPU suporta mais de 10.000 QPS. O QPS de DNS das cargas de trabalho de negócios varia significativamente. Monitore o pico de uso de CPU por pod do CoreDNS e adicione réplicas quando o uso ultrapassar um núcleo nos períodos de pico. Se o pico de uso for desconhecido, implante um pod do CoreDNS para cada oito nós do cluster como medida conservadora.
Ajustar o número de pods do CoreDNS
O número de pods do CoreDNS determina diretamente os recursos de computação disponíveis. Ajuste conforme sua avaliação.
Como o UDP não possui retransmissão, a redução de escala ou a reinicialização de pods do CoreDNS pode causar timeouts de resolução DNS em todo o cluster por até cinco minutos, caso existam defeitos de UDP com IPVS nos nós do cluster. Consulte Troubleshoot DNS resolution anomalies para soluções relacionadas ao IPVS.
-
Ajuste automático do número de pods com base em políticas recomendadas
Implante o
dns-autoscalera seguir. Ele ajusta o número de pods do CoreDNS em tempo real na proporção de um pod para cada oito nós do cluster. Contagem de réplicas:replicas = max(ceil(cores × 1/coresPerReplica), ceil(nodes × 1/nodesPerReplica)), restrita pelos limitesmaxemin. -
Ajustes manuais
Ajuste manualmente o número de pods do CoreDNS:
kubectl scale --replicas={target} deployment/coredns -n kube-system # Replace {target} with the desired pod count -
Não use autoscaling de workload
Mecanismos de autoscaling de workload como horizontal pod autoscaling (HPA) ou CronHPA provocam operações frequentes de dimensionamento. Devido a anomalias de resolução durante a redução de escala de pods, não use autoscaling de workload para pods do CoreDNS.
Ajustar as especificações dos pods do CoreDNS
Modifique as especificações dos pods para ajustar os recursos do CoreDNS. Em clusters gerenciados ACK Pro, os pods do CoreDNS têm um limite de memória padrão de 2Gi e sem limite de CPU. Defina o limite de CPU como 4096m, com mínimo de 1024m. Ajuste a configuração dos pods do CoreDNS no console.
Agendar pods do CoreDNS
Configurações de agendamento incorretas podem impedir a implantação de pods do CoreDNS e causar falha no CoreDNS. Compreenda completamente scheduling antes de prosseguir.
Implante pods do CoreDNS em múltiplas zonas e nós para evitar falhas de nó único ou zona única. Versões do CoreDNS anteriores à v1.8.4.3 usam anti-afinidade fraca de nó por padrão, o que pode concentrar todos os pods no mesmo nó quando os recursos são insuficientes. Exclua os pods para acionar o reagendamento ou atualize para a versão mais recente do componente. Versões do CoreDNS anteriores à v1.8 não recebem mais manutenção. Faça a atualização o quanto antes.
Evite implantar o CoreDNS em nós com utilização total de CPU ou memória, pois isso afeta o QPS de DNS e a latência de resposta. Use parâmetros personalizados para agendar o CoreDNS em nós dedicados e garantir resolução de nomes de domínio estável.
Otimize a configuração do CoreDNS
O Container Service for Kubernetes (ACK) fornece apenas configurações padrão do CoreDNS. Revise todos os parâmetros e otimize-os para os containers da sua aplicação. A configuração do CoreDNS é altamente flexível. Consulte DNS policy configuration and domain name resolution e a documentação oficial do CoreDNS.
As configurações padrão do CoreDNS em versões mais antigas do Kubernetes podem apresentar riscos. Verifique e otimize-as conforme descrito a seguir:
Use a inspeção programada e o diagnóstico de falhas em Container Intelligence Operations para verificar os arquivos de configuração do CoreDNS. Se o Container Intelligence Operations reportar anomalias no ConfigMap do CoreDNS, revise os itens acima.
O CoreDNS pode consumir memória adicional ao recarregar configurações. Após modificar itens de configuração, monitore o status dos pods. Se os pods apresentarem escassez de memória, aumente o limite de memória no Deployment do CoreDNS. Defina a memória como 2 GB.
Desative as configurações de afinidade do service kube-dns
As configurações de afinidade podem causar desequilíbrios significativos de carga entre as réplicas do CoreDNS. Desative-as usando um dos seguintes métodos:
Console method
Faça login no ACK console. No painel de navegação à esquerda, clique em Clusters.
Na página Clusters, clique no nome do seu cluster. No painel de navegação à esquerda, clique em .
-
No namespace kube-system, clique em Edit YAML à direita do service kube-dns.
Se sessionAffinity for
None, ignore as etapas restantes.Se sessionAffinity for
ClientIP, continue com as etapas restantes.
-
Exclua os campos sessionAffinity e sessionAffinityConfig e todas as suas subchaves. Em seguida, clique em Update.
# Delete all the following content. sessionAffinity: ClientIP sessionAffinityConfig: clientIP: timeoutSeconds: 10800 Clique em Edit YAML novamente para o service kube-dns e verifique se sessionAffinity está como
None. Nesse caso, a atualização do service kube-dns foi concluída com êxito.
Command-line method
-
Visualize a configuração do service kube-dns:
kubectl -n kube-system get svc kube-dns -o yamlSe sessionAffinity for
None, ignore as etapas restantes.Se sessionAffinity for
ClientIP, continue com as etapas restantes.
-
Abra e edite o service kube-dns:
kubectl -n kube-system edit service kube-dns -
Exclua todas as configurações relacionadas a sessionAffinity (sessionAffinity, sessionAffinityConfig e todas as subchaves). Em seguida, salve a alteração e saia.
# Delete all the following content. sessionAffinity: ClientIP sessionAffinityConfig: clientIP: timeoutSeconds: 10800 -
Após a modificação, verifique se sessionAffinity está como
None. Nesse caso, a atualização do service kube-dns foi concluída com êxito.kubectl -n kube-system get svc kube-dns -o yaml
Desative o plugin Autopath
Algumas versões mais antigas do CoreDNS têm o plugin Autopath ativado, o que pode produzir resultados de resolução incorretos em cenários extremos. Verifique se o plugin está ativado e desative-o editando o arquivo de configuração. Consulte Autopath.
Após desativar o plugin Autopath, o QPS de consultas DNS no lado do cliente pode aumentar até três vezes, e o tempo de resolução de um único domínio pode aumentar até três vezes. Monitore a carga do CoreDNS e o impacto nos negócios.
Abra o arquivo de configuração do CoreDNS com
kubectl -n kube-system edit configmap coredns.Exclua a linha
autopath @kubernetese salve a alteração.Verifique o status e os logs do pod do CoreDNS. Se os logs contiverem a palavra
reload, a modificação foi bem-sucedida.
Configure o desligamento gracioso do CoreDNS
O mecanismo lameduck do CoreDNS permite o desligamento gracioso. Quando o CoreDNS é interrompido ou reiniciado, as requisições em andamento são concluídas normalmente, em vez de serem abruptamente interrompidas. O mecanismo lameduck funciona da seguinte forma:
Quando o CoreDNS é encerrado, ele entra no modo Lameduck.
No modo
lameduck, o CoreDNS para de aceitar novas requisições, mas continua processando as requisições existentes até que sejam concluídas ou o tempo limite dolameduckexpire.
Console method
Faça login no ACK console. No painel de navegação à esquerda, clique em Clusters.
Na página Clusters, clique no nome do seu cluster. No painel de navegação à esquerda, clique em .
No namespace kube-system, clique em Edit YAML à direita do item de configuração coredns.
Certifique-se de que o plugin health está ativado e defina o tempo limite de lameduck como
15sconforme a configuração a seguir. Em seguida, clique em OK.
.:53 {
errors
# The health plugin may have different default settings in various CoreDNS versions.
# Case 1: health plugin disabled by default.
# Case 2: health plugin enabled by default but lameduck time not set.
# health
# Case 3: health plugin enabled by default with lameduck time set to 5s.
# health {
# lameduck 5s
# }
# For all three cases, modify uniformly as follows to set lameduck to 15s.
health {
lameduck 15s
}
# Do not modify other plugins; omitted here.
}
Se os pods do CoreDNS estiverem em execução normal, a configuração de desligamento gracioso foi atualizada. Se os pods apresentarem anomalias, verifique os eventos e logs dos pods para identificar a causa.
Command-line method
Abra o arquivo de configuração do CoreDNS:
Certifique-se de que o plugin
healthestá ativado e defina lameduck como15sconforme o seguinte Corefile:Salve e saia após modificar o arquivo de configuração do CoreDNS.
Se o CoreDNS estiver em execução normal, a configuração de desligamento gracioso foi atualizada. Se os pods apresentarem anomalias, verifique os eventos e logs dos pods para identificar a causa.
kubectl -n kube-system edit configmap/coredns
.:53 {
errors
# The health plugin may have different default settings in various CoreDNS versions.
# Case 1: health plugin disabled by default.
# Case 2: health plugin enabled by default but lameduck time not set.
# health
# Case 3: health plugin enabled by default with lameduck time set to 5s.
# health {
# lameduck 5s
# }
# For all three cases, modify uniformly as follows to set lameduck to 15s.
health {
lameduck 15s
}
# Do not modify other plugins; omitted here.
}
Defina o protocolo padrão do plugin Forward para comunicação com os servidores DNS upstream do VPC
O NodeLocal DNSCache se comunica com o CoreDNS via TCP. O CoreDNS utiliza o mesmo protocolo das requisições recebidas ao se comunicar com servidores DNS upstream. Por padrão, as requisições de resolução de domínios externos originadas dos containers de aplicação passam pelo NodeLocal DNSCache e pelo CoreDNS, chegando aos servidores DNS do VPC (100.100.2.136 e 100.100.2.138) via TCP.
Os servidores DNS do VPC têm suporte limitado a TCP. Com o NodeLocal DNSCache, modifique a configuração do CoreDNS para preferir UDP na comunicação DNS upstream e evitar anomalias de resolução. Modifique o ConfigMap coredns no namespace kube-system. Consulte Manage ConfigMaps. No plugin forward, especifique prefer_udp como protocolo upstream. Após essa alteração, o CoreDNS passa a preferir UDP para comunicação upstream:
# Before modification
forward . /etc/resolv.conf
# After modification
forward . /etc/resolv.conf {
prefer_udp
}
Configure o plugin de readiness probe Ready
As versões do CoreDNS posteriores à 1.5.0 exigem o plugin ready para ativar as readiness probes.
-
Abra o arquivo de configuração do CoreDNS:
kubectl -n kube-system edit configmap/coredns -
Verifique se a linha
readyestá presente. Se estiver ausente, adicioneready. Pressione Esc, digite:wq!e pressione Enter para salvar e sair.apiVersion: v1 data: Corefile: | .:53 { errors health { lameduck 15s } ready # Add this line if missing, ensuring consistent indentation with Kubernetes. kubernetes cluster.local in-addr.arpa ip6.arpa { pods verified fallthrough in-addr.arpa ip6.arpa } prometheus :9153 forward . /etc/resolv.conf { max_concurrent 1000 prefer_udp } cache 30 loop log reload loadbalance } Verifique o status e os logs do pod do CoreDNS. Se os logs contiverem a palavra
reload, a modificação foi bem-sucedida.
Configure o plugin multisocket para aprimorar o desempenho de resolução do CoreDNS
O CoreDNS v1.12.1 introduziu o plugin multisocket. Quando ativado, o CoreDNS utiliza múltiplos sockets para escutar na mesma porta, aprimorando o desempenho em cenários de alto uso de CPU. Consulte a documentação da comunidade.
Ative o multisocket no ConfigMap coredns:
.:53 {
...
prometheus :9153
multisocket [NUM_SOCKETS]
forward . /etc/resolv.conf
...
}
NUM_SOCKETS especifica o número de sockets que escutam na mesma porta.
Alinhe NUM_SOCKETS com o uso estimado de CPU, os limites de recursos de CPU e os recursos disponíveis no cluster. Por exemplo:
Se o CoreDNS consome 4 núcleos no pico e há 8 núcleos disponíveis, defina
NUM_SOCKETScomo 2.Se o CoreDNS consome 8 núcleos no pico e há 64 núcleos disponíveis, defina
NUM_SOCKETScomo 8.
Teste diferentes configurações e mensure o QPS e a carga para determinar a configuração ideal.
Se você não especificar NUM_SOCKETS, o CoreDNS utilizará GOMAXPROCS por padrão, que equivale ao limite de CPU do pod do CoreDNS ou à contagem de núcleos de CPU do nó quando nenhum limite estiver definido.