Banco de Dados

16 mar, 2015

MySQL Utilities – replicação

Publicidade

Há algum tempo a turma que desenvolve o MySQL Oracle começou com a ideia de entregar ao administrador de bancos de dados uma série de ferramentas, também conhecidas como scripts, para a realização de tarefas bem conhecidas no dia-a-dia de um DBA. Pude perceber no evento MySQL Central @ OOW 2014 que essa mesma turma estava lá e conversando com o Product Manager, Chuck Bell. Eu soube que eles realmente estão investindo tempo para se obter scripts realmente robustos e que entregue rapidamente o que se deseja obter a respeito de status dos bancos de dados, replicação, comparação de dados entre bancos rodando em instâncias diferentes e outras operações.

O que é o MySQL Utilities?

O MySQL Utilities é um conjunto de aplicativos ou scripts escritos em Python, empacotado e disponibilizado pela Oracle. Dentro deste pacote, temos acesso a vários scripts para realização de várias tarefas. Vale lembrar que o MySQL Fabric também é parte deste pacote. Neste artigo vou dar mais ênfase às operações relacionadas com scripts que administram a replicação entre servidores de bancos de dados MySQL.

Subindo nosso ambiente de testes

Para que o leitor possa colocar em prática o passo a passo deste artigo, será necessário obter duas máquinas virtuais rodando o MySQL 5.6, onde configuraremos a replicação com o protocolo GTID através dos scripts do pacote MySQL Utilities. Como eu já venho utilizando o Vagrant há bastante tempo, recomendo que você faça a tentativa de trabalhar com esse software para provisionar de maneira quase instantânea suas máquinas virtuais. Gosto de trabalhar com ele, pois, consigo já instalar o MySQL a partir do repositório da Oracle através de script que é lido no boot do sistema operacional.

Contudo, se for mais confortável criar máquinas virtuais com o seu virtualizador preferido, vamos em frente – o que você precisa é ter duas máquina rodando CentOS 6.5 + MySQL 5.6.

Ambiente e configurações do MySQL

wagnerbianchi02:mysql_utilities root# vagrant status
 Current machine states:
     black poweroff (virtualbox)
     blue poweroff (virtualbox)
     red poweroff (virtualbox)
     green poweroff (virtualbox)

Nada especial com relação às configurações de cada máquina virtual. Caso você utilize o Vagrant, baixe o Vagrantfile e o script de instalação do MySQL + MySQL Utilities clicando aqui. Ainda, você pode fazer a instalação do repositório YUM da Oracle e fazer o setup dos pacotes do MySQL 5.6 da seguinte forma:

[root@black ~]# rpm -Uvi https://dev.mysql.com/get/mysql-community-release-el6-5.noarch.rpm
[...]
[root@black ~]# yum install mysql-server mysql-utilities
[...]

Caso você já tenha o pacote do Utilities instalado, ele poderá sofrer um update. Você precisa fazer a instalação do Utilities em todos os nós ou máquinas de sua topologia de replicação (para facilitar as coisas!). Lembro que o pacote MySQL Utilities não vem com o mysql-server, portanto, temos que instalar os dois. No final, teremos o seguinte ambiente, formado por um MASTER e dois SLAVEs, onde uma quarta máquina será utilizada somente para fazermos a simulação do failover do MySQL.

Toplogia de replicação GTID

Após obter as máquinas e o MySQL 5.6 rodando, adicione os seguintes arquivo de configuração para cada MySQL – digo, o arquivo my.cnf:

#: black
[mysqld]
binlog-format=ROW
log-slave-updates=true
gtid-mode=on
enforce-gtid-consistency=true
master-info-repository=TABLE
relay-log-info-repository=TABLE
relay-log-recovery=1
sync-master-info=1
slave-parallel-workers=2
binlog-checksum=CRC32
master-verify-checksum=1
slave-sql-verify-checksum=1
binlog-rows-query-log_events=1
server-id=1
report-host=black
report-port=3306
port=3306
log-bin=black-bin.log
datadir=/var/lib/mysql
socket=/var/lib/mysql/mysql.sock

#: blue
[mysqld]
binlog-format=ROW
log-slave-updates=true
gtid-mode=on
enforce-gtid-consistency=true
master-info-repository=TABLE
relay-log-info-repository=TABLE
relay-log-recovery=1
sync-master-info=1
slave-parallel-workers=2
binlog-checksum=CRC32
master-verify-checksum=1
slave-sql-verify-checksum=1
binlog-rows-query-log_events=1
server-id=2
report-host=blue
report-port=3306
port=3306
log-bin=blue-bin.log
datadir=/var/lib/mysql
socket=/var/lib/mysql/mysql.sock

#: red
[mysqld]
binlog-format=ROW
log-slave-updates=true
gtid-mode=on
enforce-gtid-consistency=true
master-info-repository=TABLE
relay-log-info-repository=TABLE
relay-log-recovery=1
sync-master-info=1
slave-parallel-workers=2
binlog-checksum=CRC32
master-verify-checksum=1
slave-sql-verify-checksum=1
binlog-rows-query-log_events=1
server-id=3
report-host=red
report-port=3306
port=3306
log-bin=red-bin.log
datadir=/var/lib/mysql
socket=/var/lib/mysql/mysql.sock
 
#: green
[mysqld]
binlog-format=ROW
log-slave-updates=true
gtid-mode=on
enforce-gtid-consistency=true
master-info-repository=TABLE
relay-log-info-repository=TABLE
relay-log-recovery=1
sync-master-info=1
slave-parallel-workers=2
binlog-checksum=CRC32
master-verify-checksum=1
slave-sql-verify-checksum=1
binlog-rows-query-log_events=1
server-id=4
report-host=green
report-port=3306
port=3306
log-bin=green-bin.log
datadir=/var/lib/mysql
socket=/var/lib/mysql/mysql.sock

Após colocar os arquivos acima em /etc, inicie o servidores de bancos de dados MySQL e entre com os seguintes comandos para configurar os testes com o usuário root sem senha, considerado somente para facilitar os testes!

[root@black ~]# service mysqld start
Starting mysqld: [ OK ]
[root@blue ~]# service mysqld start
Starting mysqld: [ OK ]
[root@red ~]# service mysqld start
Starting mysqld: [ OK ]
[root@green ~]# service mysqld start
Starting mysqld: [ OK ]
#
[wb@black ~]$ mysql -P3306 -u root -e "GRANT ALL ON *.* TO root@'%' WITH GRANT OPTION;"
[wb@black ~]$ mysql -P3306 -u root -e "GRANT ALL ON *.* TO root@'%' WITH GRANT OPTION;"
[wb@blue ~]$ mysql -P3306 -u root -e "GRANT ALL ON *.* TO root@'%' WITH GRANT OPTION;"
[wb@red ~]$ mysql -P3306 -u root -e "GRANT ALL ON *.* TO root@'%' WITH GRANT OPTION;"
[wb@green ~]$ mysql -P3306 -u root -e "GRANT ALL ON *.* TO root@'%' WITH GRANT OPTION;"

Uma recomendação de segurança é, no caso de esse cenário ser implementado em um ambiente de produção, não trabalhar com o usuário root e, antes de prosseguir com a utilização do banco de dados, rode o aplicativo mysql_secure_installation para garantir que o usuário root tenha uma senha segura, que o banco de dados test seja removido, assim como os usuário anônimos e/ou sem uma senha configurada. Outro ponto interessante é que aqui não vamos configurar a replicação com o protocolo clássico (file/offset), vamos utilizar o novo protocolo GTID, do qual pretendo falar em um próximo artigo.

Com isso, já temos nosso ambiente montado e podemos seguir com o MySQL Utilities.

Antes mesmo de fazermos a configuração da replicação em si, precisamos fazer um checklist para verificar se os nosso servidores de bancos de dados MySQL 5.6 estão devidamente configurados, cobrindo os principais requisitos para que o ambiente não encare agora ou no futuro alguma surpresa quanto aos requisitos mínimos para seu funcionamento. Para isso, temos o script mysqlrplcheck que verifica todos os principais pontos, aprovando ou não quando há um problema, por exemplo, relacionado com um server_id não configurado ou não único (o que gera muita, mas muita dor de cabeça se for para a produção, resultando no efeito fan-in com perda de dados).

[root@black ~]# mysqlrplcheck --master=root@black --slave=root@blue
# master on black: ... connected.
# slave on blue: ... connected.
Test Description                                                     Status
---------------------------------------------------------------------------
Checking for binary logging on master                                [pass]
Are there binlog exceptions?                                         [pass]
Replication user exists?                                             [pass]
Checking server_id values                                            [pass]
Checking server_uuid values                                          [pass]
Is slave connected to master?                                        [pass]
Check master information file                                        [pass]
Checking InnoDB compatibility                                        [pass]
Checking storage engines compatibility                               [pass]
Checking lower_case_table_names settings                             [pass]
Checking slave delay (seconds behind master)                         [pass]
# ...done.
[root@black ~]# mysqlrplcheck --master=root@black --slave=root@red
# master on black: ... connected.
# slave on red: ... connected.
Test Description                                                     Status
---------------------------------------------------------------------------
Checking for binary logging on master                                [pass]
Are there binlog exceptions?                                         [pass]
Replication user exists?                                             [pass]
Checking server_id values                                            [pass]
Checking server_uuid values                                          [pass]
Is slave connected to master?                                        [pass]
Check master information file                                        [pass]
Checking InnoDB compatibility                                        [pass]
Checking storage engines compatibility                               [pass]
Checking lower_case_table_names settings                             [pass]
Checking slave delay (seconds behind master)                         [pass]
# ...done.

MySQL Utilities, mysqlreplicate

Este script é realmente um dos mais interessantes para a configuração da replicação entre os servidores de bancos de dados MySQL 5.6. Interessante por te permite configurar a replicação sem a necessidade de lidar com as possíveis complexidades que podem ser adicionadas ao comando CHANGE MASTER TO, classicamente utilizado em muitos casos em que a troca do protocolo de replicação ainda não é possível devido à criticidade do ambiente.

Vamos configurar então os servidores “blue” e “red” como SLAVEs do servidor “black”, que será inicialmente o nosso MASTER.

[root@black ~]# mysqlreplicate --master=root@black:3306 --slave=root@blue:3306 --rpl-user=root
WARNING: Using a password on the command line interface can be insecure.
# master on black: ... connected.
# slave on blue: ... connected.
# Checking for binary logging on master...
# Setting up replication...
# ...done.
[root@black ~]# mysqlreplicate --master=root@black:3306 --slave=root@red:3306 --rpl-user=root
WARNING: Using a password on the command line interface can be insecure.
# master on black: ... connected.
# slave on red: ... connected.
# Checking for binary logging on master...
# Setting up replication...
# ...done.

MySQL Utilities, mysqlrplshow e mysqlrplchk

Como de costume, precisamos verificar se a replicação foi realmente configurada e se está tudo bem. Para isso, utilizamos o script mysqlrplshow, que nos mostra no terminal as interligações de MASTER e seus SLAVEs.

[root@black ~]# mysqlrplshow --master=root@black:3306 --discover-slaves-login=root --verbose
WARNING: Using a password on the command line interface can be insecure.
# master on black: ... connected.
# Finding slaves for master: black:3306

# Replication Topology Graph
black:3306 (MASTER)
   |
   +--- blue:3306 [IO: Yes, SQL: Yes] - (SLAVE)
   |
   +--- red:3306 [IO: Yes, SQL: Yes] - (SLAVE)

O mais interessante aqui é que talvez, dependendo do seu ambiente, você não vai precisar verificar a replicação entre os servidores utilizando comando como SHOW SLAVE STATUS, ou mesmo, SHOW SLAVE HOSTS para verificar qual SLAVE ainda estão pelo menos com a IO_THREAD conectada (pode ser que um SLAVE apareça como resultado na lista de servidores do comando SHOW SLAVE HOSTS, mas localmente no próprio MySQL, a SQL_THREAD esteja parada por algum erro ao executar uma consulta qualquer).

MySQL Utilities, mysqlfailover

Para finalizar este artigo, quero mostrar o script mysqlfailover que é parte fundamental de qualquer estratégia de continuidade de qualquer empresa que utilize bancos de dados – todas! O mais interessante para este script é rodar em uma máquina separada das demais que quais o MySQL se encontra em execução. Isso porque se uma das máquinas MySQL cair ou sofrer qualquer tipo de problema, o script ainda estará em execução, podendo detectar o problema e fazer o failover do MASTER problemático, fazendo o switchover das configurações da topologia automaticamente e elegendo um novo MASTER dentre os servidores SLAVEs existentes. WOW, show!

Como podemos observar, os scripts pedem alguns inputs que são, na verdade, informações sobre os servidores com os quais estamos trabalhando. Não seria diferente com o mysqlfailover, que, no seu caso, solicita que seja apontado qual é o MASTER atual e os possíveis servidores SLAVE dos quais um será eleito novo MASTER em caso de falhas no MASTER atual, entedeu? Vamos em frente…

Seguindo essa linha, temos o seguinte comando que vamos executar na quarta máquina, o servidor “green”.

[root@green ~]# mysqlfailover --master=root@black --candidates=root@blue,root@red --discover-slaves-login=root --interval=5# Discovering slaves for master at black:3306
# Discovering slave at blue:3306
# Found slave: blue:3306
# Discovering slave at red:3306
# Found slave: red:3306
# Checking privileges.
# Checking privileges on candidates.
MySQL Replication Failover Utility
Failover Mode = auto     Next Interval = Wed Feb 25 15:38:56 2015

Master Information
------------------
Binary Log File   Position  Binlog_Do_DB  Binlog_Ignore_DB
black-bin.000013  231

GTID Executed Set
8964b605-3ab5-11e4-8706-0800274fb806:1 [...]

Replication Health Status
+--------+-------+---------+--------+------------+---------+
| host   | port  | role    | state  | gtid_mode  | health  |
+--------+-------+---------+--------+------------+---------+
| black  | 3306  | MASTER  | UP     | ON         | OK      |
| blue   | 3306  | SLAVE   | UP     | ON         | OK      |
| red    | 3306  | SLAVE   | UP     | ON         | OK      |
+--------+-------+---------+--------+------------+---------+

Q-quit R-refresh H-health G-GTID Lists U-UUIDs

O comando que executamos do mysqlfailover fará um refresh a cada 5 segundos, verificando se o MASTER está responsivo e se está tudo bem com o mesmo. Ele nos mostra na tabela a cada refresh a posição atual dos servidores de bancos de dados MySQL que atualmente são SLAVEs e também que são os possíveis candidatos para se tornarem MASTER em caso de falha. Um ponto interessante é que, para quem conhece de MHA (MySQL High-Availability), o intervalo mínimo de refresh que temos naquela solução é de 10 segundos, ou seja, o mysqlfailover consegue verificar uma falha e iniciar o switchover mais rapidamente, na metade do tempo.

Conclusão

Nessa artigo vimos alguns dos scripts que facilitam a vida do DBA na administração de servidores de bancos de dados MySQL, com foco em um ambiente escalado horizontalmente (Scale-Out), ou seja, com replicação. Numa próxima oportunidade vou tentar trazer mais sobre esse pacote e também dar ênfase à replicação GTID.