[Arquitetura] Estratégias de caching

Caching é uma prática quase que essencial para a maioria das aplicações hoje em dia. O alto consumo de informações, sistemas escalados horizontalmente e, claro, quando se usa vários serviços distintos, os benefícios do cache são claros, performance, redução dos custos de bancos e de carga nos serviços e etc. Sabendo disso, então bora analisar alguns tipos de caching e descobrir qual melhor se encaixa na sua aplicação.


Single in-memory cache (IMDG/IMDB)
Talvez o mais simples e mais conhecido, in-memory cache baseia-se na ideia de colocar um banco em memória (tipo o Redis) dentro de um serviço, salvando as consultas mais frequentes e evitando assim realizar um volume alto de queries no banco, o que aumenta a performance já que seu banco é poupado de algumas operações.

Distributed cache
O princípio é o mesmo do single in-memory cache, a diferença é que você realmente vai ter um banco apartado, onde vários serviços consomem dele antes de ir para a real fonte de dados. Por exemplo um Couchbase, onde todos os serviços contém uma lib para acessá-lo, por exemplo.

Replicated in-process cache
Similar ao single in-memory cache, cada serviço terá seu banco em memória dentro da aplicação, porém quando algum desses bancos sofrer alguma atualização, essa mudança será replicada para os outros single in-memory dos demais serviços, mantendo todos serviços com as bases atualizadas. Pensando que temos uma aplicação com várias réplicas rodando atrás de um load balancer, para que todas réplicas tenham o mesmo conteúdo cacheado, podemos colocar um Hazelcast no serviço e toda vez que uma réplica atualiza seu conteúdo, todas as outras irão atualizar sua base.

Near cache hybrid
Replicated cache é um pouco perigoso, pois o que acontece se tiver muitos dados sendo salvos? Então com isso, chegamos à última estratégia que é uma fusão de Distributed cache e Replicated cache. Para evitar o problema de muitos dados, cada aplicação terá seu in-memory, mas também teremos um distributed onde as alterações de cada aplicação refletirão nele e não nas outras aplicações como no in-process. Pense que vamos utilizar um Apache Ignite em ambos (in-memory e distributed), quando nossas réplicas começam seus updates in-memory todas as atualizações são feitas no distributed, auxiliando as outras réplicas a terem um acesso mais fácil a tal aplicação apenas quando necessitarem.

Como podemos analisar, os trade-off são bem claros entre performance e consistência. No mundo dos microsserviços e escalonamento horizontal, não vemos muitas vantagens com in-memory cache. Near cache hybrid, também teremos vários em in-memory criando uma inconsistência grande entre os serviços e irá acabar sendo usado como um distributed. Nisso ficamos entre replicated, onde temos mais performance porém mais complexidade e distributed onde temos mais consistência e simplicidade. Podemos fazer outros comparativos para essa escolha, mas aí começa a cair muita na necessidade de cada serviço. Então é isso por hoje, espero ter ajudado em sua escolha de como fazer sua camada de cache. Abraços!