Criando um cluster MongoDB com ReplicaSet e Sharding com Docker

O MongoDb certamente é um banco NoSQL muito popular e poderoso. Uma de suas grandes vantagens é estar preparado para escalar horizontalmente através do conceito de replicas (ReplicaSet) e particionamento dos dados (Shards).
Esse artigo tem o objetivo de criar um tutorial para que você possa criar o seu primeiro cluster do MongoDb com auxílio do Docker. Por simplificação, todos os containers serão instanciados em uma mesma máquina e, por isso, não é recomendado utilizar para fins de produção!
Vamos lá?
Para a criação de um cluster mongo replicante e particionado precisamos de de três tipos diferentes de serviços, são eles:
- Roteadores: responsáveis por receberem as requisições de leitura e escrita e redirecionar para a partição correta.
- Config Servers: armazenam os metadados das partições (shards). Os metadados incluem a lista de chunks de cada shard e os intervalos que definem os chunks.
- Shards: são os nós responsáveis pelo armazenamento dos dados. Cada shard fica responsável por um subconjunto dos dados do banco.

Para o nosso caso, vamos criar um cluster com três nós replicantes de configuração (ConfigServer), três shards cada um como uma réplica (totalizando seis nós) e um roteador. A figura abaixo mostra a arquitetura do cluster a ser criado:

Agora que já sabemos os serviços que serão criados, vamos ao procedimento!
Procedimento
Inicialmente vamos criar uma rede para a comunicação entre os containers. Para isso, execute o seguinte comando:
$ docker network create mongo-shardServidores de Configuração (ConfigServers)
Feito isso, vamos agora criar os containers ConfigServers. Para isso, vamos usar a imagem do mongo em seguida executar o comando para iniciar um configServer.
$ docker run --name mongo-config01 --net mongo-shard -d mongo mongod --configsvr --replSet configserver --port 27017$ docker run --name mongo-config02 --net mongo-shard -d mongo mongod --configsvr --replSet configserver --port 27017$ docker run --name mongo-config03 --net mongo-shard -d mongo mongod --configsvr --replSet configserver --port 27017
Após a iniciação dos containers do ConfigServer, é hora de configurá-los. Para isso, acesse o shell do mongo de um dos containers dos ConfigServes através do seguinte comando.
$ docker exec -it mongo-config01 mongoEm seguida execute o seguinte comando para iniciar a operação dos servidores de configuração:
Agora que os servidores de configuração já estão criados e configurados, vamos criar os Shards.
Shards
Conforme combinado, vamos criar três shards em que cada um possui uma replica, totalizando assim seis nós. Para isso, vamos utilizar a imagem do mongo com comando para iniciar em modo shard.
Shard 01
$ docker run --name mongo-shard1a --net mongo-shard -d mongo mongod --port 27018 --shardsvr --replSet shard01$ docker run --name mongo-shard1b --net mongo-shard -d mongo mongod --port 27018 --shardsvr --replSet shard01
Shard 02
$ docker run --name mongo-shard2a --net mongo-shard -d mongo mongod --port 27019 --shardsvr --replSet shard02$ docker run --name mongo-shard2b --net mongo-shard -d mongo mongod --port 27019 --shardsvr --replSet shard02
Shard 03
$ docker run --name mongo-shard3a --net mongo-shard -d mongo mongod --port 27020 --shardsvr --replSet shard03$ docker run --name mongo-shard3b --net mongo-shard -d mongo mongod --port 27020 --shardsvr --replSet shard03
Uma vez que os containers já estão criados e online, precisamos configurar e iniciar os shards. Para isso, vamos acessar o shell de cada um dos shards (shard01, shard2 e shard3) aplicando sua respectiva configuração.
$ docker exec -it mongo-shard1a mongo --port 27018Após acessar o shell do shard01, execute o seguinte comando de inicialização:
Repita o procedimento para o shard02 e shard03, tomando cuidado para ajustar os endereços dos respectivos hosts.
$ docker exec -it mongo-shard2a mongo --port 27019$ docker exec -it mongo-shard3a mongo --port 27020Feito isso, estamos quase prontos. Agora só falta subir o roteador para que os shards fiquem acessíveis.
Roteador
Para iniciar o serviço do roteador, iremos também usar a imagem do mongo com o comando de configuração do modo roteador (mongos).
$ docker run -p 27017:27017 --name mongo-router --net mongo-shard -d mongo mongos --port 27017 --configdb configserver/mongo-config01:27017,mongo-config02:27017,mongo-config03:27017 --bind_ip_allFeito isso, todos os serviços já devem estar estar online. Você pode checar se todos os serviços estão operacionais através do seguinte comando:
$ docker ps
Por fim, precisamos configurar o roteador para que ele conheça os shards disponíveis. Isso pode ser feito através dos seguintes comandos:
$ docker exec -it mongo-router mongo
$ sh.addShard("shard01/mongo-shard1a:27018")
$ sh.addShard("shard01/mongo-shard1b:27018")
$ sh.addShard("shard02/mongo-shard2a:27019")
$ sh.addShard("shard02/mongo-shard2b:27019")
$ sh.addShard("shard03/mongo-shard3a:27020")
$ sh.addShard("shard03/mongo-shard3b:27020")Feito isso, seu cluster já está prontinho! Para verificar seu funcionamento execute o seguinte comando:
sh.status()Se tudo ocorreu bem você deverá ter um resultado semelhante a imagem seguinte:

Agora é só começar a usar o cluster conectando sua aplicação ao roteador e enviar os comandos de leitura e escrita.
Experimente seu cluster simulando a indisponibilidade de algum serviço e veja como ele se comporta.
Bem, é isso! Espero que consigam configurar o cluster de vocês. Abraços e até a próxima!