Mysql
 sql >> Base de Dados >  >> RDS >> Mysql

Práticas recomendadas de replicação do MySQL


A Replicação MySQL tem sido a solução mais comum e amplamente utilizada para alta disponibilidade por grandes organizações como Github, Twitter e Facebook. Embora seja fácil de configurar, há desafios enfrentados ao usar esta solução desde a manutenção, incluindo atualizações de software, desvio de dados ou inconsistência de dados nos nós de réplica, alterações de topologia, failover e recuperação. Quando o MySQL lançou a versão 5.6, ele trouxe uma série de melhorias significativas, especialmente para a replicação que inclui IDs de transação global (GTIDs), somas de verificação de eventos, escravos multi-thread e escravos/mestres à prova de falhas. A replicação ficou ainda melhor com MySQL 5.7 e MySQL 8.0.

A replicação permite que os dados de um servidor MySQL (o primário/mestre) sejam replicados para um ou mais servidores MySQL (a réplica/escravos). A Replicação MySQL é muito fácil de configurar e é usada para dimensionar cargas de trabalho de leitura, fornecer alta disponibilidade e redundância geográfica e descarregar backups e tarefas analíticas.

Replicação MySQL na Natureza

Vamos ter uma visão geral rápida de como o MySQL Replication funciona na natureza. A Replicação do MySQL é ampla e há várias maneiras de configurá-la e como ela pode ser usada. Por padrão, ele usa replicação assíncrona, que funciona à medida que a transação é concluída no ambiente local. Não há garantia de que qualquer evento chegará a qualquer escravo. É uma relação mestre-escravo fracamente acoplada, onde:

  • O primário não espera por uma réplica.

  • A réplica determina quanto ler e de qual ponto no log binário.

  • A réplica pode ficar arbitrariamente atrás do mestre na leitura ou aplicação de alterações.

Se o primário travar, as transações que ele confirmou podem não ter sido transmitidas para nenhuma réplica. Conseqüentemente, o failover do primário para a réplica mais avançada, nesse caso, pode resultar em um failover para o primário desejado que, na verdade, está com transações ausentes em relação ao servidor anterior.

A replicação assíncrona fornece menor latência de gravação, pois uma gravação é reconhecida localmente por um mestre antes de ser gravada em escravos. É ótimo para dimensionamento de leitura, pois adicionar mais réplicas não afeta a latência da replicação. Bons casos de uso para replicação assíncrona incluem a implantação de réplicas de leitura para dimensionamento de leitura, cópia de backup em tempo real para recuperação de desastres e análises/relatórios.

Replicação semi-síncrona do MySQL

O MySQL também suporta replicação semi-síncrona, onde o mestre não confirma as transações para o cliente até que pelo menos um escravo tenha copiado a alteração em seu log de retransmissão e a tenha descarregado no disco. Para habilitar a replicação semi-síncrona, etapas extras para instalação do plug-in são necessárias e devem ser habilitadas nos nós mestre e escravo do MySQL designados.

Semi-síncrono parece ser uma solução boa e prática para muitos casos em que a alta disponibilidade e a ausência de perda de dados são importantes. Mas você deve considerar que a semi-síncrona tem um impacto no desempenho devido à viagem de ida e volta adicional e não oferece fortes garantias contra perda de dados. Quando um commit retorna com sucesso, sabe-se que os dados existem em pelo menos dois lugares (no master e em pelo menos um slave). Se o mestre confirmar, mas ocorrer um travamento enquanto o mestre estiver aguardando o reconhecimento de um escravo, é possível que a transação não tenha alcançado nenhum escravo. Isso não é um problema tão grande, pois o commit não será retornado ao aplicativo neste caso. É tarefa do aplicativo tentar novamente a transação no futuro. O que é essencial ter em mente é que quando o mestre falha e um escravo foi promovido, o antigo mestre não pode ingressar na cadeia de replicação. Em algumas circunstâncias, isso pode levar a conflitos com dados nos escravos, ou seja, quando o mestre travou depois que o escravo recebeu o evento de log binário, mas antes que o mestre obtivesse o reconhecimento do escravo). Assim, a única maneira segura é descartar os dados no mestre antigo e provisioná-los do zero usando os dados do mestre recém-promovido.

Usando o formato de replicação incorretamente

Desde o MySQL 5.7.7, o formato de log binário padrão ou a variável binlog_format usa ROW, que era STATEMENT anterior a 5.7.7. Os diferentes formatos de replicação correspondem ao método usado para registrar os eventos de log binários da origem. A replicação funciona porque os eventos gravados no log binário são lidos da origem e processados ​​na réplica. Os eventos são registrados no log binário em diferentes formatos de replicação de acordo com o tipo de evento. Não saber ao certo o que usar pode ser um problema. O MySQL tem três formatos de métodos de replicação:STATEMENT, ROW e MIXED.

  • O formato de replicação baseada em STATEMENT (SBR) é exatamente o que é – um fluxo de replicação de cada execução de instrução no mestre que será reproduzido no nó escravo. Por padrão, a replicação tradicional (assíncrona) do MySQL não executa as transações replicadas para os escravos em paralelo. Com isso, significa que a ordem das instruções no fluxo de replicação pode não ser 100% a mesma. Além disso, a repetição de uma instrução pode fornecer resultados diferentes quando não executada ao mesmo tempo que quando executada a partir da fonte. Isso leva a um estado inconsistente em relação ao primário e suas réplicas. Isso não foi um problema por muitos anos, já que muitos não executavam o MySQL com muitos threads simultâneos. No entanto, com arquiteturas modernas de várias CPUs, isso se tornou altamente provável em uma carga de trabalho normal do dia-a-dia.

  • O formato de replicação ROW fornece soluções que o SBR não possui. Ao usar o formato de log de replicação baseada em linha (RBR), a origem grava eventos no log binário que indicam como as linhas da tabela individual são alteradas. A replicação da origem para a réplica funciona copiando os eventos que representam as alterações nas linhas da tabela para a réplica. Isso significa que mais dados podem ser gerados, afetando o espaço em disco na réplica e afetando o tráfego de rede e a E/S de disco. Considere se uma instrução altera muitas linhas, digamos com uma instrução UPDATE, o RBR grava mais dados no log binário, mesmo para instruções que são revertidas. A execução de instantâneos point-in-time também pode levar mais tempo. Problemas de simultaneidade podem ocorrer devido aos tempos de bloqueio necessários para gravar grandes blocos de dados no log binário.

  • Então existe um método entre esses dois; replicação de modo misto. Esse tipo de replicação sempre replicará instruções, exceto quando a consulta contiver a função UUID(), gatilhos, procedimentos armazenados, UDFs e algumas outras exceções. O modo misto não resolverá o problema de desvio de dados e, juntamente com a replicação baseada em instruções, deve ser evitado.

Planejando ter uma configuração de vários mestres?

Replicação Circular (também conhecida como topologia em anel) é uma configuração conhecida e comum para replicação do MySQL. Ele é usado para executar uma configuração de vários mestres (veja a imagem abaixo) e geralmente é necessário se você tiver um ambiente de vários datacenters. Como o aplicativo não pode esperar que o mestre no outro datacenter reconheça as gravações, é preferível um mestre local. Normalmente, o deslocamento de incremento automático é usado para evitar conflitos de dados entre os mestres. Fazer com que dois mestres executem gravações entre si dessa maneira é uma solução amplamente aceita.

No entanto, se você precisar gravar em vários data centers no mesmo banco de dados , você acaba com vários mestres que precisam gravar seus dados entre si. Antes do MySQL 5.7.6, não havia nenhum método para fazer uma replicação do tipo mesh, então a alternativa seria usar uma replicação em anel circular.

A replicação de anel no MySQL é problemática pelos seguintes motivos:latência, alta disponibilidade e deriva de dados. Escrever alguns dados no servidor A levaria três saltos para terminar no servidor D (via servidor B e C). Como a replicação (tradicional) do MySQL é single-threaded, qualquer consulta de longa duração na replicação pode travar todo o anel. Além disso, se algum dos servidores cair, o anel será quebrado e, atualmente, nenhum software de failover pode reparar as estruturas do anel. Então, o desvio de dados pode ocorrer quando os dados são gravados no servidor A e são alterados simultaneamente no servidor C ou D.

Em geral, a replicação circular não é adequada ao MySQL e deve ser evitado a todo custo. Como foi projetado com isso em mente, o Galera Cluster seria uma boa alternativa para gravações em vários datacenters.

Parando sua replicação com grandes atualizações

Vários trabalhos em lote de manutenção geralmente executam várias tarefas, desde limpar dados antigos até calcular médias de 'curtidas' obtidas de outra fonte. Isso significa que um trabalho criará muita atividade no banco de dados em intervalos definidos e, provavelmente, gravará muitos dados de volta no banco de dados. Naturalmente, isso significa que a atividade no fluxo de replicação aumentará igualmente.

A replicação baseada em instrução replicará as consultas exatas usadas nos trabalhos em lote, portanto, se a consulta levar meia hora para ser processada no mestre, o encadeamento escravo será interrompido por pelo menos a mesma quantidade de Tempo. Isso significa que nenhum outro dado pode ser replicado e os nós escravos começarão a ficar atrás do mestre. Se isso exceder o limite de sua ferramenta de failover ou proxy, ele poderá descartar esses nós escravos dos servidores disponíveis no cluster. Se você estiver usando a replicação baseada em instrução, poderá evitar isso processando os dados do seu trabalho em lotes menores.

Agora, você pode pensar que a replicação baseada em linha não é afetada por isso, pois replicará as informações da linha em vez da consulta. Isso é parcialmente verdade, pois, para alterações de DDL, a replicação é revertida para um formato baseado em instrução. Além disso, um grande número de operações CRUD (Criar, Ler, Atualizar, Excluir) afetará o fluxo de replicação. Na maioria dos casos, essa ainda é uma operação de thread único e, portanto, cada transação aguardará que a anterior seja reproduzida por meio de replicação. Isso significa que, se você tiver alta simultaneidade no mestre, o escravo poderá travar na sobrecarga de transações durante a replicação.

Para contornar isso, o MariaDB e o MySQL oferecem replicação paralela. A implementação pode diferir por fornecedor e versão. O MySQL 5.6 oferece replicação paralela desde que as consultas sejam separadas pelo esquema. Tanto o MariaDB 10.0 quanto o MySQL 5.7 podem lidar com a replicação paralela entre esquemas, mas têm outros limites. A execução de consultas por meio de threads escravos paralelos pode acelerar seu fluxo de replicação se você estiver escrevendo muito. Caso contrário, seria melhor manter a replicação tradicional de thread único.

Gerenciando sua alteração de esquema ou DDLs

Desde o lançamento do 5.7, o gerenciamento da alteração de esquema ou alteração de DDL (Data Definition Language) no MySQL melhorou muito. Até o MySQL 8.0, os algoritmos de alterações DDL suportados são COPY e INPLACE.

  • COPY:Este algoritmo cria uma nova tabela temporária com o esquema alterado. Depois de migrar os dados completamente para a nova tabela temporária, ele troca e descarta a tabela antiga.

  • INPLACE:Este algoritmo executa operações no local da tabela original e evita a cópia e reconstrução da tabela sempre que possível.

  • INSTANT:Este algoritmo foi introduzido desde o MySQL 8.0, mas ainda tem limitações.

No MySQL 8.0, o algoritmo INSTANT foi introduzido, fazendo alterações instantâneas e no local da tabela para adição de colunas e permitindo DML concorrente com capacidade de resposta e disponibilidade aprimoradas em ambientes de produção ocupados. Isso ajuda a evitar grandes atrasos e travamentos na réplica que geralmente eram grandes problemas na perspectiva do aplicativo, fazendo com que dados obsoletos fossem recuperados, pois as leituras no escravo ainda não foram atualizadas devido ao atraso.

Embora seja uma melhoria promissora, ainda há limitações com eles, e às vezes não é possível aplicar esses algoritmos INSTANT e INPLACE. Por exemplo, para algoritmos INSTANT e INPLACE, alterar o tipo de dados de uma coluna também é uma tarefa comum de DBA, especialmente na perspectiva de desenvolvimento de aplicativos devido à alteração de dados. Essas ocasiões são inevitáveis; assim, você não pode continuar com o algoritmo COPY, pois isso trava a tabela causando atrasos no escravo. Ele também afeta o servidor primário/mestre durante essa execução, pois acumula transações de entrada que também fazem referência à tabela afetada. Você não pode executar um ALTER direto ou alteração de esquema em um servidor ocupado, pois isso acompanha o tempo de inatividade ou possivelmente corrompe seu banco de dados se você perder a paciência, especialmente se a tabela de destino for enorme.

É verdade que realizar alterações de esquema em uma configuração de produção em execução é sempre uma tarefa desafiadora. Uma solução frequentemente usada é aplicar a mudança de esquema aos nós escravos primeiro. Isso funciona bem para replicação baseada em instrução, mas isso só pode funcionar até certo ponto para replicação baseada em linha. A replicação baseada em linha permite a existência de colunas extras no final da tabela, portanto, desde que possa gravar as primeiras colunas, tudo ficará bem. Primeiro, aplique a alteração a todos os escravos, depois faça failover para um dos escravos e, em seguida, aplique a alteração ao mestre e anexe-o como escravo. Se sua alteração envolver a inserção de uma coluna no meio ou a remoção de uma coluna, isso funcionará com a replicação baseada em linha.

Existem ferramentas disponíveis que podem realizar alterações de esquema online de forma mais confiável. O Percona Online Schema Change (conhecido como pt-osc) e gh-ost por Schlomi Noach são comumente usados ​​por DBAs. Essas ferramentas lidam com alterações de esquema de forma eficaz, agrupando as linhas afetadas em partes, e essas partes podem ser configuradas de acordo, dependendo de quantos você deseja agrupar.

Se você for pular com pt-osc, esta ferramenta criará uma tabela sombra com a nova estrutura da tabela, inserirá novos dados via triggers e preencherá dados em segundo plano. Assim que terminar de criar a nova tabela, ele simplesmente trocará a antiga pela nova tabela dentro de uma transação. Isso não funciona em todos os casos, especialmente se sua tabela existente já tiver gatilhos.

Usar gh-ost primeiro fará uma cópia do seu layout de tabela existente, altere a tabela para o novo layout e, em seguida, conecte o processo como uma réplica do MySQL. Ele usará o fluxo de replicação para localizar novas linhas que foram inseridas na tabela original e, ao mesmo tempo, preencherá a tabela. Uma vez feito o preenchimento, as tabelas originais e novas serão trocadas. Naturalmente, todas as operações para a nova tabela terminarão no fluxo de replicação; assim, em cada réplica, a migração ocorre simultaneamente.

Tabelas de memória e replicação

Enquanto estamos no assunto de DDLs, um problema comum é a criação de tabelas de memória. As tabelas de memória são tabelas não persistentes, sua estrutura de tabela permanece, mas perdem seus dados após a reinicialização do MySQL. Ao criar uma nova tabela de memória em um mestre e um escravo, eles terão uma tabela vazia, que funcionará perfeitamente bem. Depois que qualquer um for reiniciado, a tabela será esvaziada e ocorrerão erros de replicação.

A replicação baseada em linha será interrompida quando os dados no nó escravo retornarem resultados diferentes, e a replicação baseada em instrução será interrompida quando tentar inserir dados que já existem. Para tabelas de memória, esse é um quebra de replicação frequente. A correção é fácil:faça uma nova cópia dos dados, altere o mecanismo para InnoDB e agora deve ser seguro para replicação.

Definindo o read_only={True|1}

Este é, obviamente, um caso possível quando você está usando uma topologia em anel, e nós desencorajamos o uso de topologia em anel se possível. Descrevemos anteriormente que não ter os mesmos dados nos nós escravos pode quebrar a replicação. Muitas vezes, isso é causado por algo (ou alguém) alterando os dados no nó escravo, mas não no nó mestre. Uma vez que os dados do nó mestre forem alterados, isso será replicado para o escravo, onde não poderá aplicar a alteração, e isso fará com que a replicação seja interrompida. Isso também pode levar à corrupção de dados no nível do cluster, especialmente se o escravo foi promovido ou falhou devido a uma falha. Isso pode ser um desastre.

A prevenção fácil para isso é certificar-se de que read_only e super_read_only (somente em> 5.6) estejam definidos em ON ou 1. Você deve ter entendido como essas duas variáveis ​​diferem e como isso afeta se você desabilitar ou habilitar eles. Com super_read_only (desde o MySQL 5.7.8) desabilitado, o usuário root pode prevenir qualquer alteração no destino ou réplica. Portanto, quando ambos estiverem desabilitados, isso impedirá que qualquer pessoa faça alterações nos dados, exceto a replicação. A maioria dos gerenciadores de failover, como ClusterControl, define esse sinalizador automaticamente para impedir que os usuários gravem no mestre usado durante o failover. Alguns deles ainda retêm isso após o failover.

Habilitando GTID

Na replicação do MySQL, iniciar o slave da posição correta nos logs binários é essencial. A obtenção dessa posição pode ser feita ao fazer um backup (xtrabackup e mysqldump suportam isso) ou quando você parou de slavar em um nó do qual está fazendo uma cópia. Iniciar a replicação com o comando CHANGE MASTER TO ficaria assim:

mysql> CHANGE MASTER TO MASTER_HOST='x.x.x.x',
MASTER_USER='replication_user', 
MASTER_PASSWORD='password', 
MASTER_LOG_FILE='master-bin.00001', 
MASTER_LOG_POS=4;

Iniciar a replicação no local errado pode ter consequências desastrosas:os dados podem ser gravados duas vezes ou não atualizados. Isso causa desvio de dados entre o nó mestre e o nó escravo.

Além disso, fazer failover de um mestre para um escravo envolve encontrar a posição correta e mudar o mestre para o host apropriado. O MySQL não retém os logs e posições binários de seu mestre, mas cria seus próprios logs e posições binários. Isso pode se tornar um problema sério para realinhar um nó escravo ao novo mestre. A posição exata do mestre no failover deve ser encontrada no novo mestre e todos os escravos podem ser realinhados.

O Oracle MySQL e o MariaDB implementaram o Global Transaction Identifier (GTID) para resolver este problema. Os GTIDs permitem o alinhamento automático dos escravos, e o servidor descobre por si mesmo qual é a posição correta. No entanto, ambos implementaram o GTID de forma diferente e, portanto, são incompatíveis. Se você precisar configurar a replicação de um para outro, a replicação deverá ser configurada com o posicionamento de log binário tradicional. Além disso, seu software de failover deve estar ciente de não usar GTIDs.

Escravo à prova de falhas

Crash safe significa que mesmo se um MySQL/OS escravo travar, você pode recuperar o escravo e continuar a replicação sem restaurar os bancos de dados MySQL no escravo. Para fazer o trabalho escravo à prova de colisão, você precisa usar apenas o mecanismo de armazenamento InnoDB e, na versão 5.6, você precisa definir relay_log_info_repository=TABLE e relay_log_recovery=1.

Conclusão

A prática leva à perfeição, mas sem o devido treinamento e conhecimento dessas técnicas vitais, pode ser problemático ou levar a um desastre. Essas práticas são comumente adotadas por especialistas em MySQL e são adaptadas por grandes indústrias como parte de seu trabalho de rotina diária ao administrar a Replicação MySQL nos servidores de banco de dados de produção.

Se você quiser ler mais sobre a Replicação do MySQL, confira este tutorial sobre replicação do MySQL para alta disponibilidade.

Para obter mais atualizações sobre soluções de gerenciamento de banco de dados e práticas recomendadas para seus bancos de dados baseados em código aberto, siga-nos no Twitter e LinkedIn e assine nossa newsletter.