Tá na moda: Microservices
Imagem: IBM Developer

Tá na moda: Microservices

Em meu último artigo, descrevi sobre a abordagem de Continuous Delivery (CD) e como ela pode beneficiar na produtividade e otimização do tempo em projetos de software. Aqui, me dedico em explicar uma abordagem de engenharia que ganhou espaço no mercado/indústria e se tornou um "emerging topic" nos artigos científicos mundo afora - Microservices!

Por definição, Microservices é uma abordagem de engenharia de software focada na decomposição de aplicativos em módulos de função única, com interfaces bem definidas que são implantadas e operadas de forma independente por equipes pequenas que possuem todo o ciclo de vida do serviço (calma, eu vou desenhar). Os Microservices aceleram a entrega minimizando a comunicação e coordenação entre as pessoas, reduzindo o escopo e o risco de mudança. Para ser mais didático, os convido a olhar para essas palavras em negrito. São os pontos chaves deste texto.

Decomposição: considere uma aplicação, que eu chamei de MyApplication. Essa aplicação possui métodos, procedimentos, ou funções, dependendo da linguagem. Neste exemplo, eu nomeei de Verify_Data, ou seja, minha aplicação vai verificar alguns dados que foram fornecidos (seja por outro sistema, ou dados alimentados por usuários). Mas minha aplicação vai fazer mais algumas coisas, como por exemplo se comunicar com um serviço web (Get_Web_Service), encontrar um serviço de impressão (Find_Printer) ou consultar um bando de dados (Find_DB). Aqui, no processo de decomposição é preciso entender que se comunicar com um serviço web não é de fato algo que verifica os dados. É um processo completamente diferente. Portanto a ideia é separar e torná-los pequenos serviços individuais.

No alt text provided for this image

Função única: usando a função Verify_Data como exemplo, essa parte do aplicativo tem uma função única para verificar os dados que são entregues. Mas não significa que essa seja a única coisa que ela faça. Essa função pode também, por exemplo, formatar as informações quando for verificada (Format_Info), ela poderia calcular e definir uma data limite (Set_Limit_Date), e poderia também enviar um pedido para o nome associado com o ID (identidade) que foi entregue (Name_From_ID). Tudo isso é, no entanto, uma única função ou um conjunto independente de processos.

No alt text provided for this image

Interfaces bem definidas: aqui, é importante ter um tipo explícito para a interface de entrada. Seguindo os exemplos anteriores, a função Verify_Data requer um ID como um inteiro. Se outro serviço vai chamar essa função, ele precisa fornecer exatamente esse tipo de dado para exatamente esse nome de função. Para completar esse ponto chave, deve haver também uma interface de saída. Por exemplo, como saída a função devolve um nome e uma data limite. Imagine um sistema de biblioteca, e que alguém está solicitando um livro que deve ser devolvido por uma data específica, digamos, em duas semanas. A interface será definida como retornando esses dados (Name/Date out).

No alt text provided for this image

Independente: em termos de codificação, vamos considerar o serviço Find_DB. Ele é responsável por encontrar bancos de dados se você precisar deles ou não. Esse serviços sabe como ir e encontrá-los. Os outros serviços é que vão verificar os dados, mas eles não sabem como encontrar esses banco de dados. Conseguiu perceber a independência? Apesar de independentes, eles precisam trabalhar juntos - a fim de retomar a informação correta do serviço Verify_Data, é necessário uma comunicação com o serviço Find_DB.

Equipes pequenas: tradicionalmente, uma equipe inteira está escrevendo código para verificar dados, escrevendo código para vincular a um serviço da Web, escrevendo código para consultar um banco de dados, e assim por diante. Voltamos à coleção original de processos que vimos anteriormente. É necessária uma grande equipe para trabalhar em tudo isso e a equipe deve coordenar seu trabalho. Nada pode ser implantado, a menos que todos tenham completado sua parte do trabalho.

No alt text provided for this image

Um arranjo melhor é dividir o trabalho e dividir a equipe. Agora, organizando Verify_Data como um objeto independente, há uma pequena equipe trabalhando nele. Find_DB é um único serviço e há outra pequena equipe trabalhando nele. Essas equipas vão trabalhar eficientemente. Eles podem se comunicar facilmente, os membros da equipe sabem a grande imagem do serviço que estão desenvolvendo, e cada serviço pode ser implantado rapidamente assim que estiver pronto. A equipe Find_DB não se importa se a equipe Verify_Data está no cronograma ou não. Eles se concentram em sua própria tarefa.

No alt text provided for this image

Todo o ciclo de vida: tradicionalmente, se uma equipe concluiu o código para o serviço Find_DB e pode ser testado, embora isso possa ser um departamento diferente, o serviço passou para outra pessoa para lidar com a construção ou implantação ou manutenção do serviço. Em Microservices, esse não é o caso. A equipe de desenvolvimento é responsável pelo teste, preparo, implantação, depuração e manutenção. Em outras palavras, o ciclo de vida completo do serviço.

No alt text provided for this image

Minimizando a comunicação: Microsserviços é sobre pessoas. Minimizar a comunicação, então, não significa que os membros da equipe devem se ignorar. A equipe é tão pequena que os membros podem falar, incessantemente. Eles podem ter reuniões de stand-up todos os dias, se quiserem. Mas eles não têm que se preocupar com a equipe maior. Realmente, a única comunicação essencial entre as equipes é concordar sobre as interfaces que cada serviço vai ter. Assim, a equipe Find_DB pode questionar e alinhar com a equipe Find_Printer qual interface eles estão fornecendo, ou se o serviço está retornando os dados corretos.

No alt text provided for this image

Reduzindo o escopo e o risco de mudança: E se for preciso modificar alguma coisa? Continuando o exemplo inicial: existe um serviço chamado Find_DB e, conforme o ciclo de vida da aplicação, vão surgindo melhoras e maneiras mais eficientes de executar o serviço. Versão 1. Versão 1.2. Versão 2.0. Essas mudanças deixariam inativos os outros serviços, como Verify_Data ou Get_Web_Service? Não.

No alt text provided for this image


O escopo da mudança está dentro da equipe. E enquanto não for alterada a interface externa, não haverá problema para outros serviços. Neste cenário, é essencial que as equipes se reunam logo no início. Todos eles precisam concordar com o formato de interface externa, de modo que a comunicação entre os serviços é claramente definida.

Voltando aos quatro Microservices que vimos no início, Verify_Data, Get_Web_Service, Find_Printer e Find_DB, você pode ver que os números de versão estão atualizando individualmente, e não há nenhuma relação entre eles. Por exemplo, pode haver uma versão 4 para Get_Web_Service, uma versão 6 para Find_DB, uma versão 5 para Find_Printer e uma versão 3 para Verify_Data.

No alt text provided for this image

Então, o que isso significa?

Tradicionalmente, um aplicativo é atualizado como um todo. Não é assim com Microservices. Os serviços são desenvolvidos e mantidos individualmente, as mudanças podem ser, e são frequentemente, feitas quase em uma base diária. No entanto, observe que isso só é possível se você estiver trabalhando na nuvem. Na nuvem, o usuário não tem conhecimento das versões. Se Verify_Data for chamado, não é necessário saber se essa é a versão usada ontem ou uma nova que foi lançada hoje de manhã. E quando Verify_Data chama Get_Web_Service, não há nenhuma necessidade de chamar uma versão específica. É só chamar.

Meu objetivo em escrever esse artigo é explicar as principais ideias e princípios de Microservices. Essa abordagem é uma ideia importante e uma consideração séria para aplicações corporativas. Apesar das experiências positivas que tenho acompanhado até agora, em comparação com aplicações monolíticas, deixo explícito aqui que ainda não há tempo suficiente para julgar completamente se, de fato, Microservices é a melhor alternativa. Alguns desafios ainda precisam ser analisados, porque em muitos casos, as verdadeiras consequências de decisões de projeto só ficam evidentes anos depois. Portanto, até que vejamos sistemas com idade suficiente, não é possível ainda concluir como as arquiteturas Microservices amadureceram.


Entre para ver ou adicionar um comentário

Outros artigos de Tiago Volpato

Outras pessoas também visualizaram

Conferir tópicos