Utilize conjuntos equilibrados de carga para clusterizar o MySQL no Linux

Importante

Os VM clássicos serão retirados a 1 de março de 2023.

Se utilizar recursos iaaS da ASM, por favor preencha a sua migração até 1 de março de 2023. Encorajamo-lo a fazer a troca mais cedo para aproveitar as muitas melhorias de funcionalidades em Azure Resource Manager.

Para mais informações, consulte a Migração dos seus recursos iaaS para a Azure Resource Manager até 1 de março de 2023.

Nota

O Azure tem dois modelos de implementação diferentes para criar e trabalhar com recursos: Azure Resource Manager e clássico. Este artigo cobre a utilização do modelo de implementação clássica. A Microsoft recomenda que as implementações mais novas utilizem o modelo Resource Manager. Um modelo Resource Manager está disponível se precisar de implementar um cluster MySQL.

A partir de 15 de novembro de 2017, as máquinas virtuais só estarão disponíveis no portal do Azure.

Este artigo explora e ilustra as diferentes abordagens disponíveis para implementar serviços altamente disponíveis baseados em Linux em Microsoft Azure, explorando a alta disponibilidade do MySQL Server como um primer. Um vídeo que ilustra esta abordagem está disponível no Canal 9.

Delinearemos uma solução de alta disponibilidade mySQL de dois dígitos, de dois sentidos, baseada em DRBD, Corosync e Pacemaker. Apenas um nó corre MySQL de cada vez. A leitura e a escrita do recurso DRBD também se limitam a apenas um nó de cada vez.

Não há necessidade de uma solução VIP como o LVS, porque você usará conjuntos equilibrados de carga em Microsoft Azure para fornecer funcionalidade de robin redondo e deteção de ponto final, remoção e recuperação graciosa do VIP. O VIP é um endereço IPv4 globalmente redirecionável atribuído por Microsoft Azure quando cria o serviço de cloud pela primeira vez.

Existem outras arquiteturas possíveis para o MySQL, incluindo o NBD Cluster, Percona, Galera, e várias soluções de middleware, incluindo pelo menos uma disponível como VM no VM Depot. Desde que estas soluções possam replicar-se em unicast vs. multicast ou transmissão e não dependem de armazenamento partilhado ou de múltiplas interfaces de rede, os cenários devem ser fáceis de implementar no Microsoft Azure.

Estas arquiteturas de agrupamento podem ser estendidas a outros produtos como PostgreSQL e OpenLDAP de forma semelhante. Por exemplo, este procedimento de equilíbrio de carga com nada partilhado foi testado com sucesso com o multi-mestre OpenLDAP, e você pode vê-lo no nosso blog channel 9.

Prepara-te

Precisa dos seguintes recursos e habilidades:

  • Uma conta Microsoft Azure com uma subscrição válida, capaz de criar pelo menos dois VMs (XS foi usado neste exemplo)
  • Uma rede e uma sub-rede
  • Um grupo de afinidade
  • Um conjunto de disponibilidade
  • A capacidade de criar VHDs na mesma região que o serviço de nuvem e anexá-los aos VMs Linux

Ambiente testado

  • Ubuntu 13.10
    • DRBD
    • Servidor MySQL
    • Corosync e Pacemaker

Grupo de afinidade

Crie um grupo de afinidade para a solução, inscrevendo-se no portal do Azure, selecionando Definições e criando um grupo de afinidade. Os recursos atribuídos criados posteriormente serão atribuídos a este grupo de afinidade.

Redes

Uma nova rede é criada e uma sub-rede é criada dentro da rede. Este exemplo utiliza uma rede de 10.10.10.0/24 com apenas uma sub-rede /24 no interior.

Máquinas virtuais

O primeiro Ubuntu 13.10 VM é criado através de uma imagem da Galeria Ubuntu e é chamado hadb01. Um novo serviço de nuvem é criado no processo, chamado Hadb. Este nome ilustra a natureza partilhada e equilibrada que o serviço terá quando mais recursos forem adicionados. A criação hadb01 é tranquila e completa através da utilização do portal. Um ponto final para SSH é criado automaticamente e a nova rede é selecionada. Agora pode criar um conjunto de disponibilidade para os VMs.

Após a criação do primeiro VM (tecnicamente, quando o serviço de nuvem é criado), crie o segundo VM, hadb02. Para o segundo VM, use Ubuntu 13.10 VM da Galeria utilizando o portal, mas use um serviço de nuvem existente, hadb.cloudapp.netem vez de criar um novo. A rede e o conjunto de disponibilidade devem ser selecionados automaticamente. Um ponto final SSH também será criado.

Após a criação de ambos os VMs, tome nota da porta SSH para hadb01 (TCP 22) e hadb02 (automaticamente atribuída pela Azure).

Armazenamento anexo

Fixe um disco novo em ambos os VMs e crie discos de 5 GB no processo. Os discos estão alojados no recipiente VHD em uso para os seus discos principais do sistema operativo. Depois de os discos serem criados e ligados, não há necessidade de reiniciar o Linux porque o núcleo verá o novo dispositivo. Este dispositivo é normalmente /dev/sdc. Verifique dmesg a saída.

Em cada VM, crie uma partição utilizando cfdisk (partição primária, linux) e escreva a nova tabela de divisórias. Não crie um sistema de ficheiros nesta partição.

Configurar o cluster

Utilize o APT para instalar Corosync, Pacemaker e DRBD em ambos os VMs Ubuntu. Para fazê-lo com apt-get, executar o seguinte código:

sudo apt-get install corosync pacemaker drbd8-utils.

Não instale o MySQL neste momento. Os scripts de instalação de Debian e Ubuntu vão inicializar um diretório de dados MySQL em /var/lib/mysql, mas como o diretório será substituído por um sistema de ficheiros DRBD, você precisa instalar o MySQL mais tarde.

Verifique (utilizando /sbin/ifconfig) que ambos os VMs estão a usar endereços na sub-rede 10.10.10.0/24 e que podem pingar-se mutuamente pelo nome. Também pode utilizar ssh-keygen e ssh-copy-id certificar-se de que ambos os VMs podem comunicar via SSH sem necessitar de uma senha.

Configurar DRBD

Crie um recurso DRBD que utilize a partição subjacente /dev/sdc1 para produzir um /dev/drbd1 recurso que pode ser formatado usando ext3 e usado em nós primários e secundários.

  1. Abrir /etc/drbd.d/r0.res e copiar a seguinte definição de recursos em ambos os VMs:

     resource r0 {
       on `hadb01` {
         device  /dev/drbd1;
         disk   /dev/sdc1;
         address  10.10.10.4:7789;
         meta-disk internal;
       }
       on `hadb02` {
         device  /dev/drbd1;
         disk   /dev/sdc1;
         address  10.10.10.5:7789;
         meta-disk internal;
       }
     }
    
  2. Inicialize o recurso utilizando drbdadm ambos os VM:

     sudo drbdadm -c /etc/drbd.conf role r0
     sudo drbdadm up r0
    
  3. No VM primário (hadb01), a propriedade da força (primária) do recurso DRBD:

     sudo drbdadm primary --force r0
    

Se examinar o conteúdo de /proc/drbd (sudo cat /proc/drbd) em ambos os VMs, deve ver Primary/Secondary sobre hadb01 e Secondary/Primary sobre hadb02, consistente com a solução neste momento. O disco de 5-GB é sincronizado sobre a rede de 10.10.10.0/24 sem custos para os clientes.

Depois de o disco ser sincronizado, pode criar o sistema de ficheiros em .hadb01 Para efeitos de teste, usamos ext2, mas o seguinte código criará um sistema de ficheiros ext3:

mkfs.ext3 /dev/drbd1

Monte o recurso DRBD

Está agora pronto para montar os recursos drbd em hadb01. Debian e derivados usam /var/lib/mysql como diretório de dados do MySQL. Como ainda não instalou o MySQL, crie o diretório e monte o recurso DRBD. Para executar esta opção, execute o seguinte código em hadb01:

sudo mkdir /var/lib/mysql
sudo mount /dev/drbd1 /var/lib/mysql

Configurar o MySQL

Agora está pronto para instalar o MySQL em hadb01:

sudo apt-get install mysql-server

Pois hadb02, tem duas opções. Pode instalar o mysql-server, que irá criar /var/lib/mysql, preenchê-lo com um novo diretório de dados e, em seguida, remover o conteúdo. Para executar esta opção, execute o seguinte código em hadb02:

sudo apt-get install mysql-server
sudo service mysql stop
sudo rm –rf /var/lib/mysql/*

A segunda opção é falhar e, em hadb02 seguida, instalar o mysql-server lá. Os scripts de instalação notarão a instalação existente e não tocá-la-ão.

Executar o seguinte código em hadb01:

sudo drbdadm secondary –force r0

Executar o seguinte código em hadb02:

sudo drbdadm primary –force r0
sudo apt-get install mysql-server

Se não planeia falhar agora com a DRBD, a primeira opção é mais fácil, embora indiscutivelmente menos elegante. Depois de configurar isto, pode começar a trabalhar na sua base de dados MySQL. Executar o seguinte código em hadb02 (ou qualquer um dos servidores está ativo, de acordo com DRBD):

mysql –u root –p
CREATE DATABASE azureha;
CREATE TABLE things ( id SERIAL, name VARCHAR(255) );
INSERT INTO things VALUES (1, "Yet another entity");
GRANT ALL ON things.\* TO root;

Aviso

Esta última declaração desativa eficazmente a autenticação para o utilizador de raiz nesta tabela. Isto deve ser substituído pelas suas declarações de SUBVENÇÃO de qualidade de produção e está incluído apenas para fins ilustrativos.

Se quiser fazer consultas de fora dos VMs (que é o objetivo deste guia), também precisa de ativar a ligação em rede para o MySQL. Em ambos os VMs, abra /etc/mysql/my.cnf e vá a bind-address. Altere o endereço de 127.0.0.1 para 0.0.0.0.0. Depois de guardar o ficheiro, emita um sudo service mysql restart na sua primária atual.

Crie o conjunto equilibrado de carga MySQL

Voltar ao portal, vá e hadb01escolha Endpoints. Para criar um ponto final, escolha o MySQL (TCP 3306) da lista de drop-down e selecione Criar um novo conjunto equilibrado de carga. Nomeie o ponto lb-mysqlfinal equilibrado de carga . Definir tempo para 5 segundos, no mínimo.

Depois de criar o ponto final, vá a hadb02, escolha Pontos finais e crie um ponto final. Escolha lb-mysqle, em seguida, selecione MySQL na lista de drop-down. Também pode utilizar o CLI Azure para este passo.

Agora tem tudo o que precisa para o funcionamento manual do cluster.

Teste o conjunto equilibrado de carga

Os testes podem ser realizados a partir de uma máquina externa utilizando qualquer cliente MySQL, ou usando certas aplicações, como phpMyAdmin funcionando como um website Azure. Neste caso, usou a ferramenta de linha de comando do MySQL noutra caixa Linux:

mysql azureha –u root –h hadb.cloudapp.net –e "select * from things;"

Falha manualmente

Pode simular falhas desligando o MySQL, trocando as primárias do DRBD e reiniciando o MySQL.

Para executar esta tarefa, execute o seguinte código em hadb01:

service mysql stop && umount /var/lib/mysql ; drbdadm secondary r0

Então, em hadb02:

drbdadm primary r0 ; mount /dev/drbd1 /var/lib/mysql && service mysql start

Depois de falhar manualmente, pode repetir a sua consulta remota e deve funcionar perfeitamente.

Configurar Corosync

Corosync é a infraestrutura de cluster subjacente necessária para que o Pacemaker funcione. Para Heartbeat (e outras metodologias como Ultramonkey), Corosync é uma divisão das funcionalidades de CRM, enquanto pacemaker permanece mais semelhante ao Heartbeat na funcionalidade.

O principal constrangimento para Corosync em Azure é que Corosync prefere multicast em vez de emissões em vez de comunicações unicast, mas Microsoft Azure networking só suporta unicast.

Felizmente, o Corosync tem um modo unicast a funcionar. O único constrangimento real é que, como todos os nós não se comunicam entre si, é necessário definir os nós nos seus ficheiros de configuração, incluindo os seus endereços IP. Podemos utilizar os ficheiros de exemplo Corosync para Unicast e alterar endereços de ligação, listas de nós e listas de registos (Ubuntu usa /var/log/corosync enquanto os ficheiros de exemplo usam /var/log/cluster), e ativar ferramentas de quórum.

Nota

Utilize a seguinte transport: udpu diretiva e os endereços IP definidos manualmente para ambos os nós.

Ver o seguinte código /etc/corosync/corosync.conf para ambos os nós:

totem {
  version: 2
  crypto_cipher: none
  crypto_hash: none
  interface {
    ringnumber: 0
    bindnetaddr: 10.10.10.0
    mcastport: 5405
    ttl: 1
  }
  transport: udpu
}

logging {
  fileline: off
  to_logfile: yes
  to_syslog: yes
  logfile: /var/log/corosync/corosync.log
  debug: off
  timestamp: on
  logger_subsys {
    subsys: QUORUM
    debug: off
    }
  }

nodelist {
  node {
    ring0_addr: 10.10.10.4
    nodeid: 1
  }

  node {
    ring0_addr: 10.10.10.5
    nodeid: 2
  }
}

quorum {
  provider: corosync_votequorum
}

Copie este ficheiro de configuração em VMs e inicie o Corosync em ambos os nós:

sudo service start corosync

Pouco depois de iniciar o serviço, o cluster deve ser estabelecido no anel atual, e o quórum deve ser constituído. Podemos verificar esta funcionalidade através da revisão de registos ou executando o seguinte código:

sudo corosync-quorumtool –l

Verá uma saída semelhante à seguinte imagem:

corosync-quorumtool -l sample output

Configurar o Pacemaker

O Pacemaker usa o cluster para monitorizar os recursos, definir quando as primárias descem e mudar esses recursos para os secundários. Os recursos podem ser definidos a partir de um conjunto de scripts disponíveis ou de scripts LSB (init-like), entre outras escolhas.

Queremos que a Pacemaker "possua" o recurso DRBD, o ponto de montagem e o serviço MySQL. Se o Pacemaker pode ligar e desligar o DRBD, montá-lo e desmontá-lo e, em seguida, iniciar e parar o MySQL na ordem certa quando algo de mau acontece com a primária, a configuração está completa.

Quando instala o Pacemaker pela primeira vez, a sua configuração deve ser bastante simples, algo como:

node $id="1" hadb01
  attributes standby="off"
node $id="2" hadb02
  attributes standby="off"
  1. Verifique a configuração executando sudo crm configure show.

  2. Em seguida, crie um ficheiro (como /tmp/cluster.conf) com os seguintes recursos:

     primitive drbd_mysql ocf:linbit:drbd \
           params drbd_resource="r0" \
           op monitor interval="29s" role="Master" \
           op monitor interval="31s" role="Slave"
    
     ms ms_drbd_mysql drbd_mysql \
           meta master-max="1" master-node-max="1" \
             clone-max="2" clone-node-max="1" \
             notify="true"
    
     primitive fs_mysql ocf:heartbeat:Filesystem \
           params device="/dev/drbd/by-res/r0" \
           directory="/var/lib/mysql" fstype="ext3"
    
     primitive mysqld lsb:mysql
    
     group mysql fs_mysql mysqld
    
     colocation mysql_on_drbd \
            inf: mysql ms_drbd_mysql:Master
    
     order mysql_after_drbd \
            inf: ms_drbd_mysql:promote mysql:start
    
     property stonith-enabled=false
    
     property no-quorum-policy=ignore
    
  3. Carregue o ficheiro na configuração. Só precisas de fazer isto num nó.

     sudo crm configure
       load update /tmp/cluster.conf
       commit
       exit
    
  4. Certifique-se de que o Pacemaker começa no arranque em ambos os nós:

     sudo update-rc.d pacemaker defaults
    
  5. Ao utilizar sudo crm_mon –L, verifique se um dos seus nós se tornou o mestre do cluster e está a executar todos os recursos. Pode usar o Monte e o PS para verificar se os recursos estão a funcionar.

A imagem que se segue mostra crm_mon com um nó parado (saída selecionando Ctrl+C):

crm_mon node stopped

Esta imagem mostra ambos os nós, um mestre e um escravo:

crm_mon operational master/slave

Testar

Estás pronto para uma simulação automática de falhas. Há duas maneiras de fazer isto: suave e duro.

A forma suave utiliza a função de paragem do cluster: crm_standby -U `uname -n` -v on. Se usares isto no mestre, o escravo assume o domínio. Lembre-se de fazer isto voltar a pôr isto de volta. Se não o fizeres, crm_mon mostrará um nó em espera.

O mais difícil é desligar o VM primário (hadb01) através do portal ou alterando o nível de funcionamento no VM (isto é, parar, desligar). Isto ajuda o Corosync e o Pacemaker a sinalizar que o mestre vai descer. Pode testá-lo (útil para janelas de manutenção), mas também pode forçar o cenário congelando o VM.

STONITH

Deve ser possível emitir uma paragem de VM através do CLI Azure em vez de um script STONITH que controla um dispositivo físico. Pode utilizar /usr/lib/stonith/plugins/external/ssh como base e ativar o STONITH na configuração do cluster. O Azure CLI deve ser instalado globalmente e as definições e perfil de publicação devem ser carregados para o utilizador do cluster.

O código de amostra para o recurso está disponível no GitHub. Alterar a configuração do cluster adicionando o seguinte a sudo crm configure:

primitive st-azure stonith:external/azure \
  params hostlist="hadb01 hadb02" \
  clone fencing st-azure \
  property stonith-enabled=true \
  commit

Nota

O guião não faz verificações para cima ou para baixo. O recurso original da SSH tinha 15 verificações de ping, mas o tempo de recuperação de um VM Azure pode ser mais variável.

Limitações

Aplicam-se as seguintes limitações:

  • O script de recursos linbit DRBD que gere o DRBD como um recurso no Pacemaker usa drbdadm down ao desligar um nó, mesmo que o nó esteja apenas em modo de espera. Isto não é o ideal porque o escravo não sincronizará o recurso DRBD enquanto o mestre recebe escritas. Se o mestre não falhar graciosamente, o escravo pode assumir um estado antigo do sistema de ficheiros. Há duas formas potenciais de resolver isto:
    • Impor um drbdadm up r0 em todos os nós de cluster através de um cão de guarda local (não clusterizado)
    • Editando o script linbit DRBD, certificando-se de que down não é chamado em /usr/lib/ocf/resource.d/linbit/drbd
  • O equilibrador de carga precisa de pelo menos cinco segundos para responder, pelo que as aplicações devem estar conscientes do cluster e ser mais tolerantes com o tempo limite. Outras arquiteturas, como filas de aplicações e middlewares de consulta, também podem ajudar.
  • A sintonização MySQL é necessária para garantir que a escrita é feita a um ritmo manejável e os caches são lavados ao disco com a maior frequência possível para minimizar a perda de memória.
  • O desempenho da escrita depende da interligação VM no interruptor virtual porque este é o mecanismo utilizado pela DRBD para replicar o dispositivo.