Banco de Dados

5 ago, 2019

Novidades da versão 4.2 do MongoDB: As transações distribuídas

Publicidade

Introdução

Antes de começar a nossa conversa, é preciso que você saiba o que são transações e conheça o sharding do MongoDB. Se você não conhece estes itens te convido a ler dois posts aqui do blog:

1 – Transações

2- Sharding 

Ahhh as transações… Até junho de 2018 eu me arriscava a dizer que elas eram uma das características dos bancos de dados relacionais, mas no MongoDB World de 2018, a foi anunciado o suporte a transações e as propriedades ACID.

Na versão 4.0 do MongoDB as transações eram suportadas em um ambiente que utilizasse a replicação, mas não eram suportadas se utilizássemos o sharding.

De lá para cá eu confesso que não senti falta deste recurso, mas eu sabia que era o caminho natural, e assim foi. No MongoDB World de 2019 o suporte às transações distribuídas foi anunciado. Se você quer testar os recursos da nova verão, vamos juntos! O MongoDB 4.2 está disponível como Release Candidate (RC) e sendo assim, podemos começar.

Transações Distribuídas?

Quando utilizamos o sharding nossos dados estão divididos em vários nós (normalmente cada nó é um replicaset ). Uma transação distribuída poderá impactar dados que estão em diversos nós.

Vamos usar transação para tudo?

Não se empolgue! As transações são muito úteis e muito importantes, mas no MongoDB precisam ser usadas com sabedoria.

Você não vai copiar os dados do seu banco de dados relacional para o MongoDB (por favor!), então se acostume com o fato de que você não usará transações em todas as operações de alteração de dados. Se você estiver fazendo isso, reveja o seu modelo de dados, porque provavelmente existem problemas nele.

A versão 4.2

Um dos aspectos que eu mais gosto do uso de transações no MongoDB, é que a sintaxe é muito parecida com a sintaxe de qualquer outro banco de dados. Abre uma transação, executa um conjunto de comandos, se todos os comandos forem executados com sucesso efetiva a transação, se ocorreu um erro em qualquer comando, desfaça todos os comandos e fecha a transação.

Quando um desenvolvedor está criando uma aplicação, nem sempre ele saberá se a coleção, ou as coleções, que ele está manipulando fazem parte de um sharding ou de um replicaset, ou se estão sendo executados em um instância local… Enfim, na minha opinião, não faz sentido exigir o conhecimento da arquitetura, e nem criar uma aplicação para cada uma delas.

No MongoDB a sintaxe para utilizar as transações é a mesma, independente da arquitetura.

Veja o exemplo abaixo escrito em Python e que é aplicável a uma transação distribuída:

with client.start_session() as s: 
    s.start_transaction() 
    collection_one.insert_one(doc_one, session=s) 
    collection_two.insert_one(doc_two, session=s) 
    s.commit_transaction()

(* exemplo retirado do paper sobre as novidades da versão 4.2)

É importante ressaltar que a atomicidade é mantida independente da arquitetura – se uma transação não for confirmada em um shard, ela será desfeita em todos os outros shards que fazem parte da transação. 

Importante saber

Como eu disse em um tópico anterior não se empolgue, mas use as transações sempre que precisar! Por isso segue uma lista de boas práticas, divulgadas pela MongoDB sobre o uso de transações distribuídas.

·         Qual a versão do driver usado pela sua aplicação? Para usar a versão 4.2 o driver precisa ter suporte a ela.

    o   Atenção ao fazer atualizações de drivers em produção! Teste primeiro e garanta a estabilidade da sua aplicação, até porque a versão 4.2 está em Release Candidate.

    o   Se você vai começar uma nova aplicação, começe com o driver atualizado.

·         O limite de tempo de execução de uma transação é de 60 segundos (por padrão). Mas ele é configurável e pode ser ajustado de acordo com o a necessidade de uso.

·         As transações que afetam dados de um único shard  devem ter o mesmo desempenho que as transações feitas em um replicaset. As transações podem afetar dados em vários shards, e isso impacta no desempenho da operação. Quanto mais shards “afetados” pela operação, mais tempo ela vai demorar. 

·         Não há limites rígidos para a quantidade de documentos que podem ser manipulados em uma transação. Como prática recomendada, não ultrapasse 1000 (em uma única transação). Se uma operação precisar modificar mais de 1000 documentos, divida a transação em partes menores  processando os documentos em lotes.

·         Se o seu replicaset contém um arbitro, e faz parte de um shard, e faz parte de uma transação, você terá problemas. As transações distribuídas apresentarão erro e serão abortadas nesta situação.

E o que mais? Mudanças nos valores da shard key

Com o MongoDB 4.2, é possível atualizar os valores da shard key, desta forma podemos mover um registro de um shard para outro. O MongoDB usará automaticamente uma transação distribuída para mover o documento para o novo shard, tendo em mente de que existe um tempo limite de 60  segundos (padrão que pode ser alterado) para que esta operação aconteça. 

Mover um documento para um novo shard, anteriormente exigia que você excluísse e, em seguida, inserisse o documento com a nova shard key, gerenciando a atomicidade das duas operações. Agora, o MongoDB detectará automaticamente o valor atualizado da shard key e moverá o documento para o shard correto.

E se der pau?

Algumas melhorias importantes precisaram ser feitas no MongoDB 4.2 para que as transações distribuídas fossem viáveis:

·         As transações podem ser maiores, de forma que não ocorra problemas com entradas de log com mais de 16MB;

·         Métricas importantes das transações distribuídas são armazenadas no log do mongod;

·         Os comandos currentOp e serverStatus foram expandidos com seções específicas de transações.

    o   Guardem estes comandos no coração! Eles sempre ajudam muito!

·         Melhorias no driver facilitam o tratamento de erros no lado da aplicação.

Por fim…

O MongoDB vem evoluindo muito e a cada versão traz muitos recursos interessantes. Conhecer o recurso é muito importante, saber quando usá-lo é fundamental!

Sucesso a todos! E semana que vem tem mais!