System design: PACELC: Uma extensão ao Teorema CAP
Tags: cap, pacelc, distributedsystems, captheorem
Published: 2023-06-07 12:14:14

O que se entende sobre o Teorema CAP? E como o Teorema PACELC extende o CAP?

No dia a dia do desenvolvimento de sistemas distribuídos, deveríamos ter a certeza de que muitas falhas, de diferentes tipos, vão acontecer. E esse é um Fato. Ignorar esses eventos abre margem para que as falácias de sistemas distribuídos entre na pauta de discussões sobre os problemas, os quais irão causar prejuízos para a arquitetura do sistema. E isso não é o que se espera de uma arquitetura robusta e tolerante a falhas, caso se tenha em consideração estratégias de design já válidas pela indústria de software.

Abaixo listo as 8 falácias sobre Sistemas Distribuídos:

1. A rede é confiável
2. A latência da minha rede é zero
3. A largura de banda da internet é grande o suficiente
4. Minha rede está segura
5. A topologia de redes não vai mudar
6. Já temos um administrador de redes
7. Não temos custo de transporte
8. Minha rede é homogênea

Durante a construção de arquiteturas desse porte, aparecerão tread-offs de todos os tipos e naturezas, e estar preparado para tomar as decisões que melhor se encaixam no seu contexto, vai fazer toda a diferença nos resultados do seu projeto.

Diante de tantos desafios encontrados durante o planejamento, desenho e execução de sistemas distribuídos, existe algum guia, princípios ou alguma forma de balancear a escolha das tecnologias e, além disso, saber onde devo melhorar a arquitetura de um sistema? Considerando as várias características exigidas nesse tipo de solução?

O Teorema CAP conta e resolve apenas uma parte da história. Apesar de atualmente ainda ser um teorema válido, existem muitas críticas a sua volta, devido algumas limitações terem sido detectadas no teorema. Então o que explica o teorema CAP? O que o faz ser uma verdade? Existe alguma alternativa?

## Teorema CAP

Criado por [Eric Brewer](https://en.wikipedia.org/wiki/Eric_Brewer_(scientist)), o [Teorema CAP](https://en.wikipedia.org/wiki/CAP_theorem), também conhecido como Brewer's theorem (Teorema de Brewer), apareceu pela primeira vez em 1998 e só foi publicado como teorema em 1999. A primeira versão do Teorema CAP, apareceu com base nos conceitos ACID, Base.

O teorema CAP afirma que um sistema distribuído não pode ter mais do que 2 propriedades, dentre as 3 possíveis: **Consistency, Availability e Partition tolerance** (_Consistência, Disponibilidade e Tolerância a partição)_

As combinações dessas escolhas se resumem em: CA, CP e AP. Dentre as combinações, CA é uma das opções que gera alguma confusão em visualizar um caso de uso, tendo em vista que se um sistema não é partition-tolerant, essa característica vai obrigar esse sistema a abrir mão da CONSISTENCY ou da AVAILABILITY em caso de falha na rede.

Portanto, o teorema CAP afirma, resumidamente, que: Na presença de falhas de rede, ou seja, partition failure, um sistema distribuído DEVE escolher entre Consistency ou Availability.


![Teorema CAP](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/4ykc4n3b9g3fxf4ivkuk.png)

### Consistency
Essa propriedade, afirma que todos os nodes possuem os mesmos dados ao mesmo tempo. Isso significa as aplicações pode ler e/ou escrever de/para qualquer um dos nós dentro dessa infraestrutura e, consequentemente, acessarão os mesmos dados.

![Consistência](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/hro5k38b0bidu1kwys8f.png)

### Availability
Essa propriedade do teorema, afirma que toda operação que for recebida por um dos nós operantes e saudáveis deve retornar uma resposta. Mesmo com um problema severo na rede ou em algum dos nós, a operação recebida pela requisição DEVE terminar e dar uma resposta.

Em resumo, essa propriedade refere-se a capacidade de um sistema permanecer acessível e operável, mesmo que 1 ou mais nós fiquem offline.

![Disponibilidade](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/kvvtblwqh95bexes2d5g.png)

### Partition tolerance
Essa propriedade do teorema trabalha sobre a perspectiva de falhas de comunicação (ou intermitências/falhas de rede) entre dois nós do sistema. Essa característica fica evidente quando os dois nós estão UP, MAS esses nós não conseguem se comunicar.

Sistemas tolerante a partição (Partition-tolerant) tem a capacidade de sustentar o funcionamento, mesmo em caso de falha de rede, ou seja, falha de comunicação entre os nós.

Os dados são suficientemente replicados em combinações de nós e redes para manter o sistema funcionando durante interrupções intermitentes.

![Tolerância a falha](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/c70si2nqb1b7bfdrn3s2.png)

## Explicando o Teorema CAP
A palavra TEOREMA assusta quem está conhecendo, pela primeira vez, esse termo, conceitos e abordagens. Até aqui já entendemos que a afirmação do teorema CAP diz que só se pode escolher 2 propriedades/características de sistema, dentre as 3 opções existentes. Por outro lado, existe uma forma que simplifica e ajuda a entender o raciocínio por trás desse teorema.

Facilita pensar no teorema CAP, quando consideramos o (P), representado por Partition tolerance, entre dois nós diferentes. É importante perceber a relevância dessa característica porque, se por meio de uma falha de comunicação, apenas um desses nós tiver seu estado atualizado, o restante ficará inconsistente, o que nos leva a ter uma perda de (C), ou seja, Consistency, no entanto, se tivermos apenas 1 nós consistente, por meio da existência de (P), perdemos (A) Availability.

O Teorema nos diz que não é possível ter um armazenamento de dados que esteja continuamente Disponível (A), Consistente (C) e Tolerante a qualquer falha (P). Porque, para ser consistente, todos os nós precisam ter o mesmo estado de atualização, na mesma ordem de ocorrência. Mas se ocorrer uma falha na comunicação, ou seja, a ocorrência de (P), as atualizações em um dos nós pode não chegar aos outros nós restantes, fazendo com que a aplicação possa ler dados desatualizados, devido ter caído em um dos nós que não foi atualizado anteriormente.

## Implicações do Teorema

- **AP**: Sistemas deste tipo respondem a consultas, mas os dados devolvidos podem nem sempre estar atualizados, com atualizações mais lentas dos dados mas “sempre” disponíveis.

- **CP**: Sistemas nessa categoria sempre retornam dados atualizados, mas alguns, ou mesmo todos os nós do sistema podem não responder se forem particionados. Ele fornece atualizações atômicas, mas pode levar a tempos limite.

- **CA**: Sistemas que se encaixam nessa categoria, sempre retornam dados atualizados quando não há partições. Por causa da última limitação, geralmente, tais sistemas são usados apenas dentro de uma máquina.

## Críticas ao Teorema
Em sistemas distribuídos, devemos assumir que vamos sim ter falhas de diferentes naturezas e não podemos evita-las, portanto, de acordo com o Teorema CAP um sistema distribuído só deveria escolher entre 2 propriedades: _Consistency ou Availability_.

Banco de dados que prezam por **ACID **(_Atomicity, Consistency, Isolation, Durability_), focam em garantir a consistência dos dados, enquanto que **BASE** (_Basically available, Soft-state, Eventually consistent_) prezam por retornar os dados presente em um dos nós, sem oferecer a garantia de que esse mesmo dado está presente em todos os outros nós.

O Teorema CAP é criticado por sua simplificação dos acontecimentos e eventos que podem acontecer em uma arquitetura de sistemas distribuídos. Uma das pessoas que compartilhou algumas críticas foi [Martin Kleppmann](https://martin.kleppmann.com/), autor do livro: **Designing Data-Intensive Applications**.

A escolha entre consistência e disponibilidade realmente só é feita quando ocorre particionamento ou falha entre os nós. Em outros momentos, nenhuma compensação é necessária. Além disso, essas escolhas podem acontecer várias vezes dentro do mesmo sistema, e essas mesmas escolhas podem mudar dependendo da natureza da operação.

Em sua definição original, **o teorema CAP ignora atrasos de tempo**, embora na prática latência e particionamento são conceitos que estão intimamente ligados. Na prática, a natureza do Teorema CAP ocorre durante um timeout, período em que o sistema deve tomar uma decisão fundamental.

Por fim, todas as três propriedades são mais contínuas do que binárias. Obviamente, a disponibilidade é contínua de 0 a 100 por cento, mas também há muitos níveis de consistência e até mesmo as partições são diferenciadas, incluindo divergências dentro do sistema sobre a existência ou não de uma partição.

## Teorema PACELC
O Teorema PACELC, criado por Daniel J. Abadi, é a extensão ao teorema CAP, considerado como abordagem alternativa focada em design de sistemas distribuídos. A fundamentação desse teorema, tem como base o modelo desenhado e definido no teorema CAP, ou seja, todas as propriedades existentes no CAP como: Consistency, Availability e Partition tolerance foram reaproveitadas e, no PACELC foi adicionada a propriedade de Latency (Latência), continuando com uma combinação lógica de exclusão entre esses conceitos.

O idealizador do PACELC, [Daniel Abadi](https://en.wikipedia.org/wiki/Daniel_Abadi), separa as operações em sistemas distribuídos em 2 modos:

Operações **COM **falhas de comunicação (_Presença da Partition_)

Operações **SEM **falhas de comunicação (_Ausência da Partition_)

A primeira parte do teorema (**PAC**) é igual ao teorema CAP, e o **ELC** é a extensão. Toda a tese assume que mantemos alta disponibilidade por replicação. Assim, quando há falha, prevalece o teorema CAP. Mas se não, ainda temos que considerar a compensação entre consistência e latência de um sistema replicado.

Isso nos leva a raciocinar que as condições para o desenho de um sistema distribuído leva sempre em consideração uma propriedade, antes de todas as outras: Partição (_Partition_), Ou seja, em havendo uma falha na comunicação (Partition) deve-se escolher uma propriedade entre Disponibilidade (_Availability_) e Consistência (_Consistency_), caso contrário, em situação normal de operação do sistema, deve-se escolher entre baixa Latência (_Latency_) (_reduzir o tempo de resposta_) e Consistência (_Consistency_).

![Teorema PACELC](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/urpzsmnsz2qst1bmgfhy.png)

## Exemplos de base de dados

- **Cassandra e DynamoDB**: São PA/EL, ou seja, eles preferem garantir disponibilidade (availability) ao invés de consistência, quando uma falha de comunicação acontece (Partition), caso contrário, eles optam por baixa latência (Latency)

- **SQLServer, MySQL, BigTable e HBase**: Por exemplo, são sistemas PC/EC: Eles sempre escolherão a consistência, abrindo mão da disponibilidade e menor latência.

## Conclusão
O teorema PACELC afirma que, em um sistema que replica dados: os teoremas CAP e PACELC ajudam os sistemas distribuídos a escolher um equilíbrio desejável entre várias características distribuídas, como consistência, disponibilidade, tolerância à partição e latência.

### Referências

- [https://en.wikipedia.org/wiki/Fallacies_of_distributed_computing](https://en.wikipedia.org/wiki/Fallacies_of_distributed_computing)
- [https://en.wikipedia.org/wiki/PACELC_theorem](https://en.wikipedia.org/wiki/PACELC_theorem)
- [https://en.wikipedia.org/wiki/CAP_theorem](https://en.wikipedia.org/wiki/CAP_theorem)
- [https://martin.kleppmann.com/2015/05/11/please-stop-calling-databases-cp-or-ap.html](https://martin.kleppmann.com/2015/05/11/please-stop-calling-databases-cp-or-ap.html)
[https://www.cl.cam.ac.uk/research/dtg/www/files/publications/public/mk428/cap-critique.pdf](https://www.cl.cam.ac.uk/research/dtg/www/files/publications/public/mk428/cap-critique.pdf)
- [https://designgurus.io/blog/system-design-interview-basics-cap-vs-pacelc](https://designgurus.io/blog/system-design-interview-basics-cap-vs-pacelc)