Esta página descreve como identificar e resolver problemas de contenção de recursos no seu ambiente do Google Distributed Cloud.
Vista geral
Por vezes, o Google Distributed Cloud pode sofrer contenção de recursos, o que faz com que os seus contentores fiquem mais lentos, tenham um desempenho inferior ou sejam terminados. Isto pode acontecer devido ao elevado consumo de CPU ou memória por parte dos contentores.
Como funciona a gestão da CPU e da memória
CPU:
- Um pod é agendado para um nó com base nos pedidos de CPU especificados pelos contentores no pod.
- Um contentor num pod não pode usar mais CPUs do que o limite especificado pelo contentor
- A utilização da CPU do contentor está limitada ao limite da CPU.
- Se a utilização da CPU for limitada ao nível do nó, os contentores são automaticamente atribuídos aos ciclos da CPU proporcionais aos pedidos.
Saiba mais sobre como os pods com pedidos de recursos são agendados.
Memória:
- Um pod é agendado para um nó com base nos pedidos de memória especificados pelos contentores no pod.
- Um contentor não pode usar mais memória do que o limite especificado pelo contentor.
- Se não for especificado um limite de memória, um contentor pode consumir toda a memória disponível num nó. Em seguida, o sistema pode acionar o OOM-Killer (Out Of Memory Killer) e desalojar os pods de baixa prioridade.
Para mais informações, consulte o seguinte:
Problemas
O contentor fica lento
Os problemas de contenção da CPU podem fazer com que os contentores fiquem lentos. Seguem-se alguns dos potenciais motivos:
Utilização elevada da CPU no contentor:
Um contentor pode ficar lento se não receber ciclos da CPU proporcionais aos pedidos da CPU ou se os pedidos da CPU tiverem sido definidos como inferiores ao que o contentor precisa. Por isso, verifique a proporção entre o limite da CPU e a utilização da CPU para o contentor.
Na Google Cloud consola > Monitorização > Explorador de métricas, no editor de MQL, execute a seguinte consulta:
fetch k8s_container
| metric 'kubernetes.io/anthos/container/cpu/limit_utilization'
| group_by 1m, [value_limit_utilization_mean: mean(value.limit_utilization)]
| filter resource.cluster_name == 'CLUSTER_NAME'
| filter resource.container_name == 'CONTAINER_NAME'
| filter resource.pod_name == 'POD_NAME'
| filter resource.namespace_name == 'NAMESPACE_NAME'
| every 1m
Em seguida, efetue um destes procedimentos:
- Se esta proporção for elevada (>=0,8), significa que o limite da CPU no contentor é baixo e o Kubernetes está a limitar os ciclos da CPU do contentor para manter a utilização da CPU dentro do limite. Para resolver este problema, aumente o limite da CPU no contentor.
- Se esta relação não for elevada (<0,8), verifique se a utilização da CPU é elevada no nó.
Utilização elevada da CPU no nó
Se a relação entre o limite da CPU e a utilização não for elevada para nenhum contentor individual do pod, é possível que o nó não tenha ciclos da CPU suficientes para atribuir ao conjunto de contentores em execução no nó. Por isso, siga estes passos para verificar a proporção da utilização real da CPU em relação às CPUs atribuíveis no nó:
Obtenha o nó do pod que está a funcionar lentamente:
kubectl get pod –kubeconfig CLUSTER_KUBECONFIG --namespace NAMESPACE POD --output wide
Na Google Cloud consola > Monitorização > Explorador de métricas, no editor de MQL, execute a seguinte consulta:
fetch k8s_node | metric 'kubernetes.io/anthos/node/cpu/allocatable_utilization' | group_by 1m, [value_allocatable_utilization_mean: mean(value.allocatable_utilization)] | filter resource.cluster_name == 'CLUSTER_NAME' | filter resource.node_name == 'NODE_NAME' | every 1m
Se esta relação for elevada (>=0,8), significa que o nó não tem ciclos de CPU suficientes e está sobreocupado. Assim, siga estes passos para verificar a utilização da CPU de todos os outros pods nesse nó e investigar se existe outro contentor a usar mais CPUs.
- Obter todos os pods no nó:
kubectl get pods --all-namespaces -o wide --field-selector spec.nodeName=NODE_NAME
- Verifique a utilização da CPU em cada contentor:
fetch k8s_container | metric 'kubernetes.io/anthos/container/cpu/limit_utilization' | group_by 1m, [value_limit_utilization_mean: mean(value.limit_utilization)] | filter resource.cluster_name == 'CLUSTER_NAME' | filter resource.container_name == 'CONTAINER_NAME' | filter resource.pod_name == 'POD_NAME' | filter resource.namespace_name == 'NAMESPACE_NAME' | every 1m
Se existir outro contentor a usar uma CPU elevada no nó, aumente os pedidos e os limites da CPU no contentor que está a funcionar lentamente. Isto recria o Pod noutro nó para obter os ciclos de CPU necessários.
Se for um Pod do sistema que está a funcionar lentamente, contacte o apoio técnico da Google.
Sobrescrição da CPU ao nível do vSphere
Se o consumo da CPU não for elevado no nó nem no pod, e o contentor continuar lento, a VM pode estar sobrecarregada ao nível do vSphere. Por conseguinte, o nó não consegue obter os ciclos de CPU esperados da virtualização subjacente.
Siga estes passos para verificar se a VM tem subscrições em excesso. Se for detetada uma subscrição excessiva, experimente o seguinte:
- Mova algumas VMs para outros anfitriões.
- Avalie e diminua o número de vCPUs por VM para o anfitrião.
- Atribua mais recursos às VMs do cluster.
- Aumente os pedidos e os limites da CPU no contentor. Isto recria o Pod noutro nó para obter os ciclos de CPU necessários.
O agrupamento é terminado por falta de memória (OOMkilled)
Os pods podem ser terminados por falta de memória devido a fugas de memória ou a uma configuração incorreta dos pedidos e limites de memória nos contentores. Seguem-se alguns dos potenciais motivos:
Utilização elevada de memória no contentor
Um pod pode ser terminado por falta de memória se qualquer contentor num pod consumir em excesso a memória total alocada. Por isso, verifique a proporção de pedidos de memória em relação aos limites de memória no contentor.
Na Google Cloud consola > Monitorização > Explorador de métricas, no editor de MQL, execute a seguinte consulta:
fetch k8s_container
| metric 'kubernetes.io/anthos/container/memory/limit_utilization'
| filter (metric.memory_type == 'non-evictable')
| group_by 1m, [value_limit_utilization_mean: mean(value.limit_utilization)]
| filter resource.cluster_name == 'CLUSTER_NAME'
| filter resource.container_name == 'CONTAINER_NAME'
| filter resource.pod_name == 'POD_NAME'
| filter resource.namespace_name == 'NAMESPACE_NAME'
| every 1m
Em seguida, efetue um destes procedimentos:
- Se esta relação for elevada (>= 0,8), aumente o limite de memória no contentor.
- Se esta relação não for elevada (<0,8), verifique se a utilização de memória no nó é elevada.
Utilização elevada da memória no nó
Um pod pode ser terminado por falta de memória se a utilização de memória de todos os pods em execução no nó exceder a memória disponível. Por isso, verifique se a condição MemoryPressure
no nó é True
.
Execute o seguinte comando e inspecione a secção
Conditions
:kubectl describe nodes --kubeconfig CLUSTER_KUBECONFIG NODE-NAME
Se a condição
MemoryPressure
forTrue
, verifique a utilização de memória no nó:fetch k8s_node | metric 'kubernetes.io/anthos/node/memory/allocatable_utilization' | filter (metric.memory_type == 'non-evictable') | group_by 1m, [value_allocatable_utilization_mean: mean(value.allocatable_utilization)] | filter resource.cluster_name == 'CLUSTER_NAME' | filter resource.node_name = 'NODE_NAME' | every 1m
Se esta proporção for elevada (>= 0,8), significa que o nó não tem memória suficiente para atribuir ao pod, possivelmente devido a alguns processos ou outros pods que consomem muita memória.
Na Google Cloud consola > Monitorização > Explorador de métricas, no editor de MQL, execute a seguinte consulta para verificar a utilização de memória dos contentores no nó:
fetch k8s_node | metric 'kubernetes.io/anthos/container_memory_usage_bytes' | filter resource.cluster_name == 'CLUSTER_NAME' | filter resource.node_name == 'NODE_NAME' | group_by 1m, [value_container_memory_usage_bytes_mean: mean(value.container_memory_usage_bytes)] | every 1m
Se existir um contentor a usar muita memória, investigue o funcionamento do contentor ou aumente o pedido de memória para o contentor, se necessário.
Se for um Pod do sistema que está a consumir muita memória, contacte o apoio técnico da Google.
Além disso, pode ativar a funcionalidade de escala automática no Google Distributed Cloud para aumentar e diminuir automaticamente a escala dos conjuntos de nós com base nas exigências das suas cargas de trabalho.
Saiba como ativar o escalamento automático.
Problemas com o etcd
Por vezes, os seus clusters do Anthos no VMware podem sofrer falhas de contentores devido a problemas do servidor etcd, e pode observar o seguinte:
Registos do servidor da API repetidos no formato:
etcdserver: request timed out
eetcdserver: leader changed
Registos etcd repetidos do formulário:
W | wal: sync duration of 2.466870869s, expected less than 1s
eW | etcdserver: read-only range request * took too long
Seguem-se alguns dos potenciais motivos:
Limitação da CPU
O servidor etcd pode estar lento devido à limitação da CPU no pod do servidor etcd e/ou no nó no qual o servidor etcd está a ser executado. Consulte os passos na secção O contentor fica lento para verificar se existem problemas de contenção da CPU.
Se detetar contenção da CPU no pod do servidor etcd ou no nó, adicione CPUs ao nó do plano de controlo do cluster de utilizador. Use gkectl update
para editar o campo cpus
no ficheiro de configuração do cluster de utilizadores.
Etcd Pod OOMkilled
O pod etcd pode ser terminado devido a problemas de contenção de recursos. Consulte os passos na secção O pod é terminado por falta de memória (Out of Memory-Killed) para verificar se existem problemas de contenção de memória com o pod do servidor etcd e/ou o nó no qual o servidor etcd está a ser executado.
Se detetar OOMkills para o pod etcd, aumente a memória disponível para o nó do plano de controlo do cluster de utilizadores. Use gkectl update
para editar o campo memoryMB
no ficheiro de configuração do cluster de utilizadores.
Lentidão do disco
Se não existirem problemas com o consumo de CPU ou memória no pod ou no nó do servidor etcd, o etcd pode estar lento se o armazenamento de dados subjacente estiver lento ou limitado.
Verifique se existem os seguintes problemas:
Para verificar se o servidor etcd está a demorar demasiado tempo a ler/escrever no disco subjacente:
Obtenha os registos do etcd:
kubectl –kubeconfig ADMIN_CLUSTER_KUBECONFIG logs -n ETCD_POD_NAMESPACE ETCD_POD
Procure as entradas do seguinte padrão para detetar se o etcd está a demorar demasiado tempo a ler a partir do disco:
W | etcdserver: read-only range request "key:\"/registry/configmaps/default/clusterapi-vsphere-controller-manager-leader-election\" " with result "range_response_count:1 size:685" took too long (6.893127339s) to execute
Procure as entradas do seguinte padrão para detetar se o etcd está a demorar demasiado tempo a escrever no disco:
W | wal: sync duration of 2.466870869s, expected less than 1s
Se algum ou ambos os padrões de registo acima forem apresentados com frequência nos registos do etcd, indica que o disco está lento. Em seguida, verifique o desempenho do arquivo de dados e dos discos.
Para verificar as métricas do etcd:
Obtenha as latências de sincronização do WAL do etcd:
Na Google Cloud consola > Monitorização > Explorador de métricas, no editor de MQL, execute a seguinte consulta:
fetch k8s_container::kubernetes.io/anthos/etcd_disk_wal_fsync_duration_seconds | every 1m | filter resource.cluster_name == 'CLUSTER_NAME' | filter resource.pod_name == 'POD_NAME' | filter resource.namespace_name == 'NAMESPACE_NAME' | percentile 99
Obtenha as latências de escrita do etcd:
Na Google Cloud consola > Monitorização > Explorador de métricas, no editor de MQL, execute a seguinte consulta:
fetch k8s_container::kubernetes.io/anthos/etcd_disk_backend_commit_duration_seconds | every 1m | filter resource.cluster_name == 'CLUSTER_NAME' | filter resource.pod_name == 'POD_NAME' | filter resource.namespace_name == 'NAMESPACE_NAME' | percentile 99
Se o valor
p99
paraetcd_disk_wal_fsync_duration_seconds
for continuamente superior a 10 ms e/ou o valorp99
paraetcd_disk_backend_commit_duration_seconds
for continuamente superior a 25 ms, indica que o disco está lento. Em seguida, verifique o desempenho do arquivo de dados e dos discos.
Latências de leitura/escrita no disco da VM
Siga estes passos para verificar as latências de leitura/escrita no disco virtual da VM
Identifique o nó do pod etcd lento:
kubectl –kubeconfig ADMIN_CLUSTER_KUBECONFIG get pods -n ETCD_POD_NAMESPACE ETCD_POD -owide
Inicie sessão no vSphere e selecione a VM identificada no passo acima: No vSphere, aceda a Monitor > Performance > Advanced e selecione Virtual Disk na secção View para identificar as latências de leitura e escrita dos discos virtuais.
Se a latência de leitura/escrita do disco virtual for elevada:
- Examine outras VMs em execução no banco de dados para verificar a utilização elevada de operações de entrada/saída por segundo (IOPS). Se alguma MV apresentar picos nos IOPS, avalie o funcionamento dessa MV.
- Consulte a sua equipa de laboratório/infraestrutura para se certificar de que a largura de banda de leitura e escrita não é limitada em nenhum momento.
- Consulte a sua equipa de laboratório/infraestrutura para identificar problemas de desempenho do disco e desempenho do armazenamento, se existirem.
Para mais informações, consulte as práticas recomendadas para dimensionar os seus recursos.
Problemas do servidor da API
Se os contentores na sua experiência do Google Distributed Cloud tiverem latência durante a comunicação com o servidor da API ou os comandos Kubectl falharem ou demorarem demasiado tempo a responder, isto pode indicar problemas com o servidor da API.
Seguem-se alguns dos potenciais motivos:
Volume elevado de pedidos de API
O servidor da API pode demorar a responder se a frequência e o volume dos pedidos forem demasiado elevados. O tempo de resposta lento pode persistir mesmo depois de o servidor da API começar a limitar os pedidos. Por isso, verifique a taxa de pedidos de API no servidor de API.
Na Google Cloud consola > Monitorização > Explorador de métricas, no editor de MQL, execute a seguinte consulta:
fetch k8s_container::kubernetes.io/anthos/apiserver_request_total
| filter resource.cluster_name == 'CLUSTER_NAME'
| filter resource.pod_name == 'APISERVER_POD_NAME'
| filter resource.namespace_name == 'NAMESPACE_NAME'
| align rate(1m)
| every 1m
| group_by [metric.verb]
Se houver um aumento inesperado nos pedidos de API, use o registo de auditoria da nuvem para identificar o pod que pode estar a consultar o servidor de API com demasiada frequência.
- Se for um Pod do sistema, contacte o apoio técnico da Google.
- Se for um pod de utilizador, investigue mais a fundo para determinar se os pedidos de API são esperados.
Limitação da CPU
Uma taxa de pedidos elevada no servidor da API pode levar à limitação da CPU. Em seguida, o servidor da API pode ficar lento devido à contenção da CPU no pod do servidor da API e/ou no nó.
Consulte a secção O contentor fica lento para verificar se existem problemas de contenção da CPU com o pod e/ou o nó.
O pod do servidor da API foi terminado por falta de memória
O pod do servidor da API pode ser terminado devido a problemas de contenção de recursos. Consulte os passos na secção O pod é terminado por falta de memória (OOMkilled) para verificar se existem problemas de contenção de memória com o pod e/ou o nó.
Respostas etcd lentas
O servidor da API baseia-se na comunicação com o cluster etcd para publicar pedidos de leitura / escrita aos clientes. Se o etcd for lento ou não responder, o servidor da API também fica lento.
Obtenha os registos do servidor da API para verificar se o servidor da API está lento devido a problemas do etcd:
kubectl –kubeconfig ADMIN_CLUSTER_KUBECONFIG logs -n APISERVER_NAMESPACE APISERVER_POD_NAME
Se observar os registos recorrentes, como etcdserver: request timedout
ou etcdserver: leader changed
, siga os passos em Problemas do Etcd para resolver problemas relacionados com o disco.
Se o seu cluster não exportar métricas
As técnicas apresentadas anteriormente neste documento baseiam-se na exportação de métricas do cluster para um Google Cloud projeto.
Se o seu cluster não exportar métricas, pode usar a linha de comandos para investigar a contenção de recursos. Seguem-se alguns comandos que pode executar na sua estação de trabalho de administrador para ver métricas.
Ver métricas de um nó:
kubectl --kubeconfig CLUSTER_KUBECONFIG get --raw \ /apis/metrics.k8s.io/v1beta1/nodes/NODE_NAME | jq
Substitua o seguinte:
- CLUSTER_KUBECONFIG: o caminho do ficheiro kubeconfig do cluster
- NODE_NAME: o nome do nó
Ver métricas de um Pod:
kubectl --kubeconfig CLUSTER_KUBECONFIG get --raw \ /apis/metrics.k8s.io/v1beta1/namespaces/NAMESPACE/pods/POD_NAME | jq
Substitua o seguinte:
- NAMESPACE: o espaço de nomes do agrupamento
- POD_NAME: o nome do agrupamento
Veja as métricas de todos os nós:
kubectl --kubeconfig CLUSTER_KUBECONFIG top node
Ver métricas de todos os pods num espaço de nomes:
kubectl --kubeconfig CLUSTER_KUBECONFIG top pod --namespace NAMESPACE
Ver métricas para os contentores em todos os pods num espaço de nomes:
kubectl --kubeconfig CLUSTER_KUBECONFIG top pod --containers --namespace NAMESPACE
Para mais informações, consulte os artigos kubectl top pod e kubectl top node.
Também pode executar o comando top a partir de um contentor em execução num nó.
Seguem-se duas formas de executar um comando num contentor:
Na estação de trabalho de administração, execute o comando kubectl exec para obter um shell no contentor. Execute o comando na shell.
Estabeleça uma ligação SSH a um nó. Em seguida, use docker exec para obter um shell no contentor. Execute o comando na shell.
O que se segue?
Se precisar de assistência adicional, contacte o apoio ao cliente do Google Cloud.
Também pode consultar o artigo Receber apoio técnico para mais informações sobre recursos de apoio técnico, incluindo o seguinte:
- Requisitos para abrir um registo de apoio técnico.
- Ferramentas para ajudar a resolver problemas, como registos e métricas.
- Componentes suportados, versões e funcionalidades do Google Distributed Cloud para VMware (apenas software).