Balanceamento de carga

Concluído

A necessidade de balanceamento de carga na computação resulta de dois requisitos básicos: Primeiro, a alta disponibilidade pode ser aprimorada por replicação. Segundo, o desempenho pode ser aprimorado por meio do processamento paralelo. Alta disponibilidade é a propriedade de um serviço que fica disponível quase 100% do tempo quando qualquer cliente tenta acessá-lo. A QoS (Qualidade de Serviço) de um serviço específico geralmente inclui vários aspectos, como os requisitos de taxa de transferência e latência.

O que é balanceamento de carga?

A forma mais conhecida de balanceamento de carga é o "DNS round robin", que muitos serviços Web de grande porte empregam para fazer o balanceamento de carga das solicitações entre vários servidores. Especificamente, vários servidores Web front-end, cada um com um endereço IP exclusivo, compartilham um nome DNS. Para balancear o número de solicitações em cada um desses servidores Web, grandes empresas como o Google mantêm e coletam um pool de endereços IP associados a cada entrada DNS. Quando um cliente faz uma solicitação (por exemplo, para o domínio www.google.com), o DNS do Google seleciona um dos endereços disponíveis do pool e o envia para o cliente. A estratégia mais simples empregada para expedir endereços IP é usar uma fila de round robin simples. Com esse método, depois de cada resposta DNS, a lista de endereços é permutada.

Antes do advento da nuvem, o balanceamento de carga de DNS era uma forma simples de lidar com a latência das conexões de longa distância. O dispatcher no servidor DNS era programado para responder com o endereço IP do servidor que ficava geograficamente mais próximo ao cliente. Os esquemas mais simples para fazer isso tentavam responder com o endereço IP do pool que era numericamente o mais próximo do endereço IP do cliente. Esse método, claro, não era confiável, pois os endereços IP não são distribuídos em uma hierarquia global. As técnicas atuais são mais sofisticadas e contam com um mapeamento de endereços IP por software para locais com base em mapas físicos dos ISPs (provedores de serviços de Internet). Como isso é implementado como uma pesquisa de software dispendiosa, esse método produz resultados mais precisos, mas sua computação é cara. No entanto, o custo de uma pesquisa lenta é reduzido, uma vez que a pesquisa de DNS ocorre somente quando a primeira conexão com um servidor é feita pelo cliente. Todas as comunicações posteriores ocorrem diretamente entre o cliente e o servidor proprietário do endereço IP expedido. Um exemplo de esquema de balanceamento de carga de DNS é mostrado na figura a seguir.

Balanceamento de carga em um ambiente de hospedagem de nuvem.

Figura 4: balanceamento de carga em um ambiente de hospedagem de nuvem

A desvantagem desse método é que, em caso de falha do servidor, a mudança para um endereço IP diferente depende da configuração de TTL (vida útil) do cache DNS. É sabido que as entradas DNS têm vida útil longa e que as atualizações levam mais de uma semana para serem propagadas pela Internet. Sendo assim, é difícil "ocultar" rapidamente uma falha do servidor do cliente. Esse aspecto pode ser aprimorado com a redução da validade (TTL) de um endereço IP no cache, mas isso tem um custo de desempenho e gera um aumento do número de pesquisas.

Frequentemente, o balanceamento de carga moderno se refere ao uso de uma instância (ou de um par de instâncias) dedicada que direciona o tráfego de entrada para os servidores de back-end. Para cada solicitação de entrada em uma porta especificada, o balanceador de carga redireciona o tráfego para um dos servidores de back-end com base em uma estratégia de distribuição. Fazendo isso, o balanceador de carga mantém os metadados da solicitação, incluindo informações como os cabeçalhos de protocolo de aplicativo (como cabeçalhos HTTP). Nessa situação, a existência de informações obsoletas não é um problema, pois toda solicitação passa pelo balanceador de carga.

Embora todos os tipos de balanceadores de carga de rede simplesmente encaminhem as informações do usuário junto com qualquer contexto para os servidores de back-end, quando se trata de fornecer a resposta de volta ao cliente, eles podem empregar uma das duas estratégias básicas:1

  • Uso de proxy: nessa abordagem, o balanceador de carga recebe a resposta do back-end e a transmite de volta para o cliente. O balanceador de carga se comporta como um proxy Web padrão e está envolvido nas duas metades de uma transação de rede, ou seja, no encaminhamento da solicitação ao cliente e no envio da resposta de volta.
  • Entrega TCP: nessa abordagem, a conexão TCP com o cliente é passada para o servidor back-end. Portanto, o servidor envia a resposta diretamente para o cliente, sem passar pelo balanceador de carga.

Mecanismo de entrega TCP do dispatcher para o servidor de back-end.

Figura 5: Mecanismo de entrega TCP do dispatcher para o servidor back-end

Impacto sobre a disponibilidade e o desempenho

O balanceamento de carga é uma estratégia importante para mascarar as falhas de um sistema. Desde que o cliente do sistema esteja exposto a apenas um ponto de extremidade que esteja balanceando a carga entre vários recursos, falhas em recursos individuais podem ser ocultadas do cliente simplesmente atendendo à solicitação em outro recurso. No entanto, é importante observar que o balanceador de carga agora é um ponto único de falha para o serviço. Se ele falhar por qualquer motivo, mesmo que todos os servidores de back-end ainda estejam funcionando, nenhuma solicitação do cliente poderá ser atendida. Portanto, para ter alta disponibilidade, os balanceadores de carga costumam ser implementados em pares.

O balanceamento de carga permite que o serviço distribua as cargas de trabalho entre vários recursos de computação na nuvem. Ter apenas uma instância de computação na nuvem gera várias limitações. Nós abordamos anteriormente a limitação física do desempenho, quando mais recursos são necessários quando as cargas de trabalho aumentam. Usando o balanceamento de carga, volumes de cargas de trabalho maiores são distribuídos entre vários recursos, para que cada recurso possa atender às próprias solicitações de maneira independente e paralela, aprimorando assim a taxa de transferência do aplicativo. Isso também aprimora os tempos médios de serviço, pois há mais servidores para atender à carga de trabalho.

Os serviços de verificação e monitoramento são fundamentais para permitir o sucesso das estratégias de balanceamento de carga. O balanceador de carga precisa garantir que cada solicitação seja atendida ao garantir que cada nó de recurso esteja disponível. Caso contrário, o tráfego não será direcionado para esse nó específico. O monitoramento com eco de ping é uma das táticas mais populares para verificar a integridade de um nó de recurso específico. Além da integridade do nó, algumas estratégias de balanceamento de carga exigem informações adicionais, como taxa de transferência, latência e utilização da CPU, para avaliar qual é o recurso mais adequado para direcionar o tráfego.

Os balanceadores de carga muitas vezes precisam garantir a alta disponibilidade. A maneira mais simples de fazer isso é criar várias instâncias de balanceamento de carga (cada uma com um endereço IP exclusivo) e vincular cada uma delas a um endereço DNS. Sempre que falha por algum motivo, uma instância do balanceador de carga é substituída por uma nova e todo o tráfego é passado para a instância de failover, com um pequeno impacto sobre o desempenho. Simultaneamente, uma nova instância do balanceador de carga pode ser configurada para substituir a que falhou e os registros DNS devem ser atualizados imediatamente.

Estratégias de balanceamento de carga

Há várias estratégias de balanceamento de carga na nuvem.

Expedição igualitária

Essa é uma abordagem estática para o balanceamento de carga, em que um algoritmo de round robin simples é usado para dividir o tráfego entre todos os nós de maneira uniforme, sem levar em consideração a utilização de nenhum nó de recurso individual no sistema nem o tempo de execução de nenhuma solicitação. Essa abordagem tenta manter todos os nós no sistema ocupados e é uma das mais simples de implementar. Uma desvantagem importante dela é que solicitações pesadas do cliente podem ser agregadas e podem atingir os mesmos datacenters, fazendo com que alguns nós fiquem sobrecarregados, enquanto outros permanecem subutilizados. No entanto, isso requer um padrão de carga muito específico e tem pouca probabilidade de ocorrer na prática em um grande número de clientes e servidores com capacidade e distribuição de conexão razoavelmente uniformes. Entretanto, essa estratégia dificulta a implementação no datacenter de estratégias de cache que levam em consideração aspectos como a localização espacial (em que você busca previamente e armazena em cache dados próximos aos que foram buscados no momento), uma vez que a solicitação seguinte feita pelo mesmo cliente pode acabar em um servidor diferente.

A AWS usa essa abordagem em sua oferta de ELB (balanceador de carga elástico). O ELB da AWS provisiona balanceadores de carga que balanceiam o tráfego entre as instâncias de EC2 anexadas. Os balanceadores de carga propriamente ditos são, essencialmente, instâncias de EC2, com um serviço específico para rotear o tráfego. Como os recursos por trás do balanceador de carga são escalados horizontalmente, os endereços IP dos novos recursos são atualizados no registro DNS do balanceador de carga. Esse processo leva vários minutos para ser concluído, pois exige tempo de monitoramento e de provisionamento. Esse período de dimensionamento (o tempo necessário para que o balanceador de carga possa lidar com a carga mais alta) é conhecido como "aquecimento" do balanceador de carga.

Os balanceadores de carga de ELB da AWS também monitoram cada recurso anexado para distribuição da carga de trabalho, a fim de manter uma verificação de integridade. Um mecanismo de eco de ping é usado para garantir que todos os recursos estejam íntegros. Os usuários do ELB podem configurar os parâmetros da verificação de integridade especificando os atrasos e o número de novas tentativas.

Distribuição baseada em hash

Essa abordagem tenta garantir que, a qualquer momento, as solicitações feitas por um cliente por meio da mesma conexão sempre terminem no mesmo servidor. Além disso, para balancear a distribuição do tráfego de solicitações, ela é feita em ordem aleatória. Essa abordagem tem várias vantagens em relação à de round robin, pois ajuda em aplicativos com reconhecimento de sessão em que a persistência de estado e as estratégias de cache podem ser muito mais simples. Ela também é menos suscetível a padrões de tráfego que resultariam na sobrecarga de um servidor, uma vez que a distribuição é aleatória, esse risco ainda existe. No entanto, como cada solicitação precisa ser avaliada quanto aos metadados de conexão para ser roteada para um servidor relevante, ela introduz uma pequena latência para cada solicitação.

O Azure Load Balancer usa um mecanismo de distribuição baseado em hash desse tipo para distribuir a carga. Esse mecanismo cria um hash para cada solicitação com base no IP de origem, na porta de origem, no IP de destino, na porta de destino e no tipo de protocolo a fim de garantir que todos os pacotes da mesma conexão sempre cheguem ao mesmo servidor. A função de hash é escolhida de modo a tornar a distribuição de conexões para os servidores aleatória.

O Azure fornece verificações de integridade por meio de três tipos de investigações: Investigações de Agente Convidado (em VMs de PaaS), investigações personalizadas HTTP e investigações personalizadas TCP. As três investigações fornecem uma verificação de integridade dos nós de recursos por meio de um mecanismo de eco de ping.

Outras estratégias são usadas para balancear a carga entre vários recursos. Cada uma delas usa métricas diferentes para medir qual é o nó de recurso mais apropriado para uma solicitação:

  • Estratégias baseadas no tempo de execução da solicitação: Essas estratégias usam um algoritmo de agendamento de prioridade, em que os tempos de execução da solicitação são usados para avaliar a ordem mais apropriada de distribuição de carga. O principal desafio no uso dessa abordagem é prever com precisão o tempo de execução de uma solicitação específica.
  • Estratégias baseadas na utilização de recursos: essas estratégias usam a utilização da CPU em cada nó de recurso para balancear a utilização entre cada nó. Os balanceadores de carga mantêm uma lista ordenada dos recursos com base em sua utilização e, em seguida, direcionam as solicitações para o nó menos carregado.

Outros benefícios

Ter um balanceador de carga centralizado possibilita várias estratégias que podem aumentar o desempenho do serviço. No entanto, é importante observar que essas estratégias funcionam enquanto o balanceador de carga não está sob uma carga insuperável. Caso contrário, o próprio balanceador de carga se torna o gargalo. Algumas dessas estão são listadas abaixo:

  • Descarregamento de SSL: transações de rede via SSL têm um custo extra associado, pois precisam ter processamento de criptografia e autenticação. Em vez de atender a todas as solicitações via SSL, a conexão do cliente com o balanceador de carga pode ser feita via SSL, enquanto as solicitações de redirecionamento para cada servidor individual podem ser feitas por HTTP. Isso reduz consideravelmente a carga sobre os servidores. Além disso, a segurança é mantida desde que as solicitações de redirecionamento não sejam feitas em uma rede aberta.
  • Buffer de TCP: é uma estratégia para descarregar clientes com conexões lentas no balanceador de carga, a fim de reduzir a carga dos servidores que estão fornecendo respostas a esses clientes.
  • Cache: em determinados cenários, o balanceador de carga pode manter um cache para as solicitações mais populares (ou solicitações que podem ser manipuladas sem serem enviadas para os servidores, como conteúdo estático) para reduzir a carga nos servidores.
  • Modelagem de tráfego: para alguns aplicativos, um balanceador de carga pode ser usado para atrasar/repriorizar o fluxo de pacotes, de modo que o tráfego possa ser moldado de maneira a se adequar à configuração do servidor. Isso afeta a QoS de algumas solicitações, mas garante que a carga de entrada possa ser atendida.

Referências

  1. Aron, Mohit e Sanders, Darren e Druschel, Peter e Zwaenepoel, Willy (2000). Scalable content-aware request distribution in cluster-based network servers, Anais da Conferência Técnica Anual da USENIX de 2000

Verificar seu conhecimento

1.

Considere o cenário a seguir. Você está usando o Azure Load Balancer com um agendador de round robin como um front-end para dois servidores Web. Um servidor é uma instância média com dois núcleos e 8 GB de RAM. O outro é uma instância grande com quatro núcleos e 16 GB de RAM. Qual dos cenários a seguir é provável?