Se você estiver executando aplicativos em clusters Standard, o kube-dns será o
provedor de DNS padrão que ajuda a ativar a descoberta e a
comunicação de serviços. Este documento descreve como gerenciar o DNS com o kube-dns,
incluindo arquitetura, configuração e práticas recomendadas para otimizar a resolução de DNS
no ambiente do GKE.
Este documento é destinado a desenvolvedores, administradores e arquitetos responsáveis por gerenciar o DNS no GKE. Para saber mais sobre papéis e tarefas comuns no Google Cloud, consulte Funções e tarefas de usuário comuns do GKE Enterprise.
Antes de começar, familiarize-se com os serviços do Kubernetes e os conceitos gerais de DNS.
Entender a arquitetura do kube-dns
O kube-dns opera no cluster do GKE para ativar a resolução de DNS entre pods e serviços.
O diagrama a seguir mostra como seus pods interagem com o serviço kube-dns:
Principais componentes
O kube-dns inclui os seguintes componentes principais:
- Pods
kube-dns:executam o software do servidorkube-dns. Várias réplicas desses pods são executadas no namespacekube-systeme oferecem alta disponibilidade e redundância. - Serviço
kube-dns:este Serviço do Kubernetes do tipoClusterIPagrupa os podskube-dnse os expõe como um único endpoint estável. OClusterIPatua como o servidor DNS do cluster, que os pods usam para enviar consultas DNS. Okube-dnsaceita até 1.000 endpoints por serviço headless. kube-dns-autoscaler:esse pod ajusta o número de réplicaskube-dnscom base no tamanho do cluster, que inclui o número de nós e núcleos de CPU. Essa abordagem ajuda a garantir que okube-dnspossa lidar com cargas de consultas de DNS variadas.
Resolução de DNS interna
Quando um pod precisa resolver um nome DNS no domínio do cluster, como
myservice.my-namespace.svc.cluster.local, o seguinte processo ocorre:
- Configuração de DNS do pod:o
kubeletem cada nó configura o arquivo/etc/resolv.confdo pod. Esse arquivo usa oClusterIPdo serviçokube-dnscomo o servidor de nomes. - Consulta DNS:o pod envia uma consulta DNS ao serviço
kube-dns. - Resolução de nomes:o
kube-dnsrecebe a consulta. Ele procura o endereço IP correspondente nos registros DNS internos e responde ao pod. - Comunicação:o pod usa o endereço IP resolvido para se comunicar com o serviço de destino.
Resolução de DNS externa
Quando um pod precisa resolver um nome DNS externo ou um nome fora do domínio do cluster, o kube-dns atua como um resolvedor recursivo. Ele encaminha a consulta
para servidores DNS upstream configurados no arquivo
ConfigMap. Você também pode configurar resolvedores personalizados para domínios específicos, também conhecidos como domínios de stub. Essa configuração direciona o kube-dns para encaminhar
solicitações desses domínios para servidores DNS upstream específicos.
Configurar o DNS do pod
No GKE, o agente kubelet em cada nó configura as definições de DNS
para os pods executados nesse nó.
Configurar o arquivo /etc/resolv.conf
Quando o GKE cria um pod, o agente kubelet modifica o arquivo /etc/resolv.conf do pod. Esse arquivo configura o servidor DNS para resolução de nomes
e especifica domínios de pesquisa. Por padrão, o kubelet configura o pod para usar o serviço DNS interno do cluster, kube-dns, como servidor de nomes. Ele também
preenche os domínios de pesquisa no arquivo. Com eles, é possível usar nomes não qualificados em consultas DNS. Por exemplo, se um pod consultar myservice, o Kubernetes primeiro tentará resolver myservice.default.svc.cluster.local, depois myservice.svc.cluster.local e, em seguida, outros domínios da lista search.
O exemplo a seguir mostra uma configuração /etc/resolv.conf padrão:
nameserver 10.0.0.10
search default.svc.cluster.local svc.cluster.local cluster.local c.my-project-id.internal google.internal
options ndots:5
Esse arquivo tem as seguintes entradas:
nameserver: define oClusterIPdo serviçokube-dns.search: define os domínios de pesquisa que são anexados a nomes não qualificados durante as buscas de DNS.options ndots:5: define o limite para quando o GKE considera um nome totalmente qualificado. Um nome é considerado totalmente qualificado se tiver cinco ou mais pontos.
Os pods configurados com a definição hostNetwork: true herdam a configuração de DNS do host e não consultam kube-dns diretamente.
Personalizar kube-dns
O kube-dns oferece uma resolução de DNS padrão robusta. É possível personalizar o comportamento dele
para necessidades específicas, como melhorar a eficiência da resolução ou usar resolvedores
de DNS preferidos. Para configurar os domínios de stub e os servidores de nomes upstream, modifique o ConfigMap kube-dns no namespace kube-system.
Modificar o ConfigMap kube-dns
Para modificar o ConfigMap kube-dns, faça o seguinte:
Abra o ConfigMap para edição:
kubectl edit configmap kube-dns -n kube-systemNa seção
data, adicione os camposstubDomainseupstreamNameserversa:apiVersion: v1 kind: ConfigMap metadata: labels: addonmanager.kubernetes.io/mode: EnsureExists name: kube-dns namespace: kube-system data: stubDomains: | { "example.com": [ "8.8.8.8", "8.8.4.4" ], "internal": [ # Required if your upstream nameservers can't resolve GKE internal domains "169.254.169.254" # IP of the metadata server ] } upstreamNameservers: | [ "8.8.8.8", # Google Public DNS "1.1.1.1" # Cloudflare DNS ]Salve o ConfigMap. O
kube-dnsrecarrega automaticamente a configuração.
Domínios stub
Os domínios de stub permitem definir resolvedores DNS personalizados para domínios específicos. Quando um pod consulta um nome nesse domínio stub, o kube-dns encaminha a consulta para o resolvedor especificado em vez de usar o mecanismo de resolução padrão.
Você inclui uma seção stubDomains no kube-dns ConfigMap.
Esta seção especifica o domínio e os servidores de nomes upstream correspondentes.
Em seguida, kube-dns encaminha consultas de nomes dentro desse domínio para os servidores designados. Por exemplo, é possível encaminhar todas as consultas DNS de internal.mycompany.com para 192.168.0.10 e adicionar "internal.mycompany.com": ["192.168.0.10"] a stubDomains.
Quando você define um resolvedor personalizado para um domínio de stub, como example.com,
o kube-dns encaminha todas as solicitações de resolução de nome para esse domínio, incluindo
subdomínios como *.example.com, para os servidores especificados.
Servidores de nomes upstream
É possível configurar o kube-dns para usar servidores de nomes upstream personalizados e resolver
nomes de domínio externos. Essa configuração instrui o kube-dns a encaminhar todas as solicitações de DNS, exceto as do domínio interno do cluster (*.cluster.local), para os servidores upstream designados. Domínios internos, como
metadata.internal e *.google.internal, podem não ser resolvidos pelos seus
servidores upstream personalizados. Se você ativar a
federação de identidade da carga de trabalho para GKE ou
tiver cargas de trabalho que dependam desses domínios, adicione um domínio stub para internal em
ConfigMap. Use 169.254.169.254, o endereço IP do servidor de metadados, como o
resolver para esse domínio stub.
Gerenciar uma implantação personalizada do kube-dns
Em um GKE padrão, o kube-dns é executado como uma implantação. Uma implantação
kube-dns personalizada significa que você, como administrador do cluster, pode controlar
a implantação e personalizá-la de acordo com suas necessidades, em vez de usar a implantação padrão
fornecida pelo GKE.
Motivos para uma implantação personalizada
Considere uma implantação personalizada do kube-dns pelos seguintes motivos:
- Alocação de recursos:ajuste os recursos de CPU e memória para pods
kube-dnse otimize o desempenho em clusters com alto tráfego de DNS. - Versão da imagem:use uma versão específica da imagem
kube-dnsou mude para um provedor de DNS alternativo, como o CoreDNS. - Configuração avançada:personalize níveis de geração de registros, políticas de segurança e comportamento de cache de DNS.
Escalonamento automático para implantações personalizadas
O kube-dns-autoscaler integrado funciona com a implantação kube-dns padrão.
Se você criar uma implantação kube-dns personalizada, o escalonador automático integrado não a gerenciará. Portanto, é necessário configurar um escalonador automático separado, especificamente
configurado para monitorar e ajustar a contagem de réplicas da sua implantação personalizada.
Essa abordagem envolve a criação e a implantação da sua própria configuração de escalonador automático no cluster.
Ao gerenciar uma implantação personalizada, você é responsável por todos os componentes dela, como manter a imagem do escalonador automático atualizada. O uso de componentes desatualizados pode levar à degradação da performance ou a falhas de DNS.
Para instruções detalhadas sobre como configurar e gerenciar sua própria implantação do kube-dns, consulte Como configurar uma implantação personalizada do kube-dns.
Resolver problemas
Para informações sobre como resolver problemas com kube-dns, consulte as seguintes páginas:
- Para receber orientações sobre
kube-dnsno GKE, consulte Resolver problemas dekube-dnsno GKE. - Para dicas gerais sobre como diagnosticar problemas de DNS do Kubernetes, consulte Como depurar a resolução de DNS.
Otimizar a resolução de DNS
Nesta seção, descrevemos problemas comuns e práticas recomendadas para gerenciar o DNS no GKE.
Limite de domínios de pesquisa dnsConfig de um pod
O Kubernetes limita o número de domínios de pesquisa DNS a 32. Se você tentar
definir mais de 32 domínios de pesquisa em um dnsConfig de um pod, o kube-apiserver
não vai criar o pod, com um erro semelhante a este:
The Pod "dns-example" is invalid: spec.dnsConfig.searches: Invalid value: []string{"ns1.svc.cluster-domain.example", "my.dns.search.suffix1", "ns2.svc.cluster-domain.example", "my.dns.search.suffix2", "ns3.svc.cluster-domain.example", "my.dns.search.suffix3", "ns4.svc.cluster-domain.example", "my.dns.search.suffix4", "ns5.svc.cluster-domain.example", "my.dns.search.suffix5", "ns6.svc.cluster-domain.example", "my.dns.search.suffix6", "ns7.svc.cluster-domain.example", "my.dns.search.suffix7", "ns8.svc.cluster-domain.example", "my.dns.search.suffix8", "ns9.svc.cluster-domain.example", "my.dns.search.suffix9", "ns10.svc.cluster-domain.example", "my.dns.search.suffix10", "ns11.svc.cluster-domain.example", "my.dns.search.suffix11", "ns12.svc.cluster-domain.example", "my.dns.search.suffix12", "ns13.svc.cluster-domain.example", "my.dns.search.suffix13", "ns14.svc.cluster-domain.example", "my.dns.search.suffix14", "ns15.svc.cluster-domain.example", "my.dns.search.suffix15", "ns16.svc.cluster-domain.example", "my.dns.search.suffix16", "my.dns.search.suffix17"}: must not have more than 32 search paths.
O kube-apiserver retorna essa mensagem de erro em resposta a uma tentativa de criação de pod. Para resolver esse problema, remova os caminhos de pesquisa extras da configuração.
Limite de nameservers upstream para kube-dns
O kube-dns limita o número de valores upstreamNameservers a três. Se você definir mais de três, o Cloud Logging vai mostrar um erro semelhante a este:
Invalid configuration: upstreamNameserver cannot have more than three entries (value was &TypeMeta{Kind:,APIVersion:,}), ignoring update
Nesse cenário, kube-dns ignora a configuração upstreamNameservers e continua usando a configuração válida anterior. Para resolver esse problema, remova
o upstreamNameservers extra do kube-dns ConfigMap.
Aumentar o escalonamento vertical de kube-dns
Em clusters Standard, use um valor menor para nodesPerReplica
para que mais pods kube-dns sejam criados quando os nós do cluster escalonar verticalmente. É altamente recomendável definir um valor explícito para o campo max para garantir que a máquina virtual (VM) do plano de controle do GKE não fique sobrecarregada devido ao grande número de pods kube-dns que monitoram a API Kubernetes.
É possível definir o valor do campo max como o número de nós no cluster.
Se o cluster tiver mais de 500 nós, defina o valor do campo max como
500.
É possível modificar o número de réplicas de kube-dns editando o
kube-dns-autoscaler ConfigMap.
kubectl edit configmap kube-dns-autoscaler --namespace=kube-system
O resultado será o seguinte:
linear: '{"coresPerReplica":256, "nodesPerReplica":16,"preventSinglePointFailure":true}'
O número de réplicas de kube-dns é calculado usando a seguinte fórmula:
replicas = max( ceil( cores * 1/coresPerReplica ) , ceil( nodes * 1/nodesPerReplica ) )
Para escalonar verticalmente, mude o valor do campo nodesPerReplica para um valor menor
e inclua um valor para o campo max.
linear: '{"coresPerReplica":256, "nodesPerReplica":8,"max": 15,"preventSinglePointFailure":true}'
Essa configuração cria um pod kube-dns para cada oito nós no cluster. Um cluster de 24 nós tem três réplicas, e um cluster de 40 nós tem cinco réplicas. Se o cluster ultrapassar 120 nós, o número de réplicas de kube-dns não vai ultrapassar 15, que é o valor do campo max.
Para garantir um nível básico de disponibilidade de DNS no cluster, defina uma contagem mínima de réplicas para o campo kube-dns.
A saída do kube-dns-autoscaler ConfigMap com o campo min configurado é semelhante a esta:
linear: '{"coresPerReplica":256, "nodesPerReplica":8,"max": 15,"min": 5,"preventSinglePointFailure":true}'
Melhorar os tempos de busca DNS
Vários fatores podem causar alta latência com buscas DNS ou falhas de resolução de DNS
com o provedor kube-dns padrão. Os aplicativos podem apresentar esses problemas como erros getaddrinfo EAI_AGAIN, que indicam uma falha temporária na resolução de nomes. As causas incluem:
- Buscas DNS frequentes na sua carga de trabalho.
- Alta densidade de pods por nó.
- Executar
kube-dnsem VMs spot ou preemptivas, o que pode levar a exclusões inesperadas de nós. - Alto volume de consultas que excede a capacidade da instância
dnsmasqno podkube-dns. Uma única instânciakube-dnstem um limite de 200 conexões TCP simultâneas no GKE versão 1.31 e mais recente, e um limite de 20 conexões TCP simultâneas no GKE versão 1.30 e anteriores.
Para melhorar os tempos de busca DNS, faça o seguinte:
- Evite executar componentes críticos do sistema, como
kube-dnsem VMs Spot ou preemptivas. Crie pelo menos um pool de nós com VMs padrão e sem VMs Spot ou preemptivas. Use taints e tolerâncias para garantir que as cargas de trabalho críticas sejam programadas nesses nós confiáveis. - Ative o NodeLocal
DNSCache. O NodeLocal
DNSCache armazena em cache as respostas de DNS diretamente em cada nó, o que reduz a latência
e a carga no serviço
kube-dns. Se você ativar o NodeLocal DNSCache e usar políticas de rede com regras de negação padrão, adicione uma política para permitir que as cargas de trabalho enviem consultas DNS aos podsnode-local-dns. - Aumente a escala vertical de
kube-dns. - Verifique se o aplicativo usa funções baseadas em
dns.resolve*em vez dedns.lookup, porquedns.lookupé síncrono. - Use nomes de domínio totalmente qualificados (FQDNs), por exemplo,
https://google.com./em vez dehttps://google.com/.
Falhas de resolução de DNS podem ocorrer durante upgrades cluster do GKE
devido a upgrades simultâneos de componentes do plano de controle, incluindo kube-dns.
Essas falhas normalmente afetam uma pequena porcentagem de nós. Teste completamente os upgrades de cluster em um ambiente que não seja de produção antes de aplicá-los aos clusters de produção.
Garantir a descoberta de serviços
O kube-dns só cria registros DNS para serviços que têm endpoints. Se um
serviço não tiver endpoints, o kube-dns não vai criar registros DNS para
esse serviço.
Gerenciar discrepâncias de TTL de DNS
Se o kube-dns receber uma resposta DNS de um resolvedor de DNS upstream com um TTL grande ou infinito, ele vai manter esse valor de TTL. Esse comportamento pode criar uma discrepância entre a entrada em cache e o endereço IP real.
O GKE resolve esse problema em versões específicas do plano de controle, como 1.21.14-gke.9100 e mais recentes ou 1.22.15-gke.2100 e mais recentes. Essas versões definem um valor máximo de TTL como 30 segundos para qualquer resposta DNS que tenha um TTL maior. Esse comportamento é semelhante ao NodeLocal DNSCache.
Conferir métricas de kube-dns
É possível recuperar métricas sobre consultas de DNS no cluster diretamente dos
kube-dns pods.
Encontre os pods
kube-dnsno namespacekube-system:kubectl get pods -n kube-system --selector=k8s-app=kube-dnsO resultado será o seguinte:
NAME READY STATUS RESTARTS AGE kube-dns-548976df6c-98fkd 4/4 Running 0 48m kube-dns-548976df6c-x4xsh 4/4 Running 0 47mEscolha um dos pods e configure o encaminhamento de portas para acessar as métricas dele:
- A porta
10055expõe métricaskube-dns. - A porta
10054expõe métricasdnsmasq.
Substitua
POD_NAMEpelo nome do pod escolhido.POD_NAME="kube-dns-548976df6c-98fkd" # Replace with your pod name kubectl port-forward pod/${POD_NAME} -n kube-system 10055:10055 10054:10054O resultado será o seguinte:
Forwarding from 127.0.0.1:10054 -> 10054 Forwarding from 127.0.0.1:10055 -> 10055- A porta
Em uma nova sessão do terminal, use o comando
curlpara acessar os endpoints de métricas.# Get kube-dns metrics curl http://127.0.0.1:10055/metrics # Get dnsmasq metrics curl http://127.0.0.1:10054/metricsA saída será semelhante a esta:
kubedns_dnsmasq_errors 0 kubedns_dnsmasq_evictions 0 kubedns_dnsmasq_hits 3.67351e+06 kubedns_dnsmasq_insertions 254114 kubedns_dnsmasq_max_size 1000 kubedns_dnsmasq_misses 3.278166e+06
A seguir
- Leia uma visão geral do DNS do cluster no GKE.
- Leia DNS para serviços e pods para uma visão geral de como o DNS é usado nos clusters do Kubernetes.
- Saiba como configurar o NodeLocal DNSCache.
- Saiba como configurar uma implantação personalizada do kube-dns.