Editar

Share via


Migrar uma aplicação monolítica para microsserviços com a conceção orientada por domínios

ASP.NET

Este artigo descreve como utilizar o design baseado em domínios (DDD) para migrar uma aplicação monolítica para microsserviços.

Normalmente, uma aplicação monolítica é um sistema de aplicações no qual todos os módulos relevantes são empacotados em conjunto como uma única unidade de execução implementável. Por exemplo, pode ser uma Aplicação Web Java (WAR) em execução no Tomcat ou num ASP. Aplicação NET em execução no IIS. Uma aplicação monolítica típica utiliza um design em camadas, com camadas separadas para IU, lógica de aplicação e acesso a dados.

Uma arquitetura monolítica típica

Estes sistemas começam pequenos, mas tendem a crescer ao longo do tempo para satisfazer as necessidades empresariais. A dada altura, à medida que são adicionadas novas funcionalidades, uma aplicação monolítica pode começar a sofrer com os seguintes problemas:

  • As partes individuais do sistema não podem ser dimensionadas de forma independente, porque estão fortemente acopladas.
  • É difícil manter o código, devido ao acoplamento apertado e às dependências ocultas.
  • Os testes tornam-se mais difíceis, aumentando a probabilidade de introdução de vulnerabilidades.

Estes problemas podem tornar-se um obstáculo ao crescimento e à estabilidade futuros. As equipas desconfiam de fazer alterações, especialmente se os programadores originais já não estiverem a trabalhar no projeto e os documentos de design forem escassos ou desatualizados.

Apesar destas limitações, um design monolítico pode fazer sentido como ponto de partida para uma aplicação. Os monólitos são, muitas vezes, o caminho mais rápido para criar uma prova de conceito ou um produto mínimo viável. Nas primeiras fases do desenvolvimento, os monólitos tendem a ser:

  • É mais fácil criar porque existe uma única base de código partilhado.
  • É mais fácil de depurar, porque o código é executado num único processo e espaço de memória.
  • Mais fácil de pensar, porque existem menos partes móveis.

No entanto, à medida que a aplicação cresce em complexidade, estas vantagens podem desaparecer. Os monólitos grandes tornam-se, muitas vezes, progressivamente mais difíceis de criar, depurar e raciocinar. A dada altura, os problemas superam os benefícios. Este é o ponto em que pode fazer sentido migrar a aplicação para uma arquitetura de microsserviços. Ao contrário dos monólitos, os microsserviços são normalmente unidades de execução descentralizadas e livremente conjugadas. O diagrama seguinte mostra uma arquitetura de microsserviços típica:

Uma arquitetura de microsserviços típica

Migrar um monólito para um microsserviço requer tempo e investimento significativos para evitar falhas ou ultrapassagens. Para garantir que qualquer migração é bem-sucedida, é bom compreender os benefícios e os desafios que os microsserviços trazem. Os benefícios incluem:

  • Os serviços podem evoluir de forma independente com base nas necessidades dos utilizadores.
  • Os serviços podem ser dimensionados de forma independente para satisfazer a procura dos utilizadores.
  • Com o tempo, os ciclos de desenvolvimento tornam-se mais rápidos, uma vez que as funcionalidades podem ser lançadas mais rapidamente no mercado.
  • Os serviços são isolados e são mais tolerantes à falha.
  • Um único serviço que falhe não irá desativar toda a aplicação.
  • Os testes tornam-se mais coerentes e consistentes com o desenvolvimento orientado pelo comportamento.

Para obter mais informações sobre os benefícios e desafios dos microsserviços, veja Estilo de arquitetura de microsserviços.

Aplicar design orientado por domínio

Qualquer estratégia de migração deve permitir que as equipas refatorizem incrementalmente a aplicação em serviços mais pequenos, ao mesmo tempo que fornecem continuidade de serviço aos utilizadores finais. Eis a abordagem geral:

  • Pare de adicionar funcionalidades ao monólito.
  • Divida o front-end a partir do back-end.
  • Decompor e desassociar o monólito numa série de microsserviços.

Para ajudar a facilitar esta decomposição, uma abordagem de desenvolvimento de software viável consiste em aplicar os princípios da estruturação baseada em domínios (DDD).

Domain Driven Design (DDD) é uma abordagem de desenvolvimento de software introduzida pela primeira vez por Eric Evans. O DDD requer uma boa compreensão do domínio para o qual a aplicação será escrita. Os conhecimentos de domínio necessários para criar a aplicação residem nas pessoas que a compreendem — os especialistas em domínio.

A abordagem DDD pode ser aplicada retroativamente a uma aplicação existente, como forma de começar a decompor a aplicação.

  1. Comece com uma linguagem omnipresente, um vocabulário comum que é partilhado entre todos os intervenientes.

  2. Identifique os módulos relevantes na aplicação monolítica e aplique-lhes o vocabulário comum.

  3. Defina os modelos de domínio da aplicação monolítica. O modelo de domínio é um modelo abstrato do domínio de negócio.

  4. Definir contextos vinculados para os modelos. Um contexto vinculado é o limite dentro de um domínio onde se aplica um modelo de domínio específico. Aplicar limites explícitos com modelos e responsabilidades claramente definidos.

Os contextos vinculados identificados no passo 4 são candidatos à refatorização em microsserviços mais pequenos. O diagrama seguinte mostra o monólito existente com os contextos vinculados sobrepostos:

Contextos vinculados dentro de um monólito

Para obter mais informações sobre como utilizar uma abordagem DDD para arquiteturas de microsserviços, veja Utilizar a análise de domínio para modelar microsserviços.

Utilizar código cola (camada anti-corrupção)

Embora este trabalho de investigação seja realizado para inventariar a aplicação monolítica, é possível adicionar novas funcionalidades ao aplicar os princípios do DDD como serviços separados. "Glue code" permite que a aplicação monolítica chame chamadas proxy para o novo serviço para obter novas funcionalidades.

 Colar Código para permitir que um monólito interaja com um novo serviço

O código glue (padrão de adaptador) atua eficazmente como uma camada anti-corrupção, garantindo que o novo serviço não é poluído por modelos de dados exigidos pela aplicação monolítica. O código glue ajuda a mediar interações entre os dois e garante que apenas os dados necessários para o novo serviço são transmitidos para ativar a compatibilidade.

Através do processo de refatorização, as equipas podem inventariar a aplicação monolítica e identificar candidatos para refatorização de microsserviços, ao mesmo tempo que estabelecem novas funcionalidades com novos serviços.

Para obter mais informações sobre camadas anti-corrupção, veja Anti-Corruption Layer pattern (Padrão de Camada Anti-Corrupção).

Criar uma camada de apresentação

O próximo passo é separar a camada de apresentação da camada de back-end. Numa aplicação de n camadas tradicional, a camada de aplicação (empresa) tende a ser os componentes essenciais para a aplicação e têm lógica de domínio dentro das mesmas. Estas APIs agregadas interagem com a camada de acesso a dados para obter dados persistentes a partir de uma base de dados. Estas APIs estabelecem um limite natural para a camada de apresentação e ajudam a desassociar a camada de apresentação num espaço de aplicação separado.

O diagrama seguinte mostra a camada de apresentação (IU) dividida das camadas de lógica de aplicação e acesso a dados.

Padrão do gateway de API

Este diagrama também apresenta outra camada, o gateway de API, que se encontra entre a camada de apresentação e a lógica da aplicação. O gateway de API é uma camada de fachada que fornece uma interface consistente e uniforme com a qual a camada de apresentação interage, ao mesmo tempo que permite que os serviços a jusante evoluam de forma independente, sem afetar a aplicação. O Gateway de API pode utilizar uma tecnologia como o Azure Gestão de API e permite que a aplicação interaja de forma RESTful.

O escalão de apresentação pode ser desenvolvido em qualquer linguagem ou arquitetura em que a equipa tenha conhecimentos, como uma aplicação de página única ou uma aplicação MVC. Estas aplicações interagem com os microsserviços através do gateway através de chamadas HTTP padrão. Para obter mais informações sobre os Gateways de API, veja Utilizar gateways de API em microsserviços.

Começar a extinguir o monólito

Nesta fase, a equipa pode começar a descascar a aplicação monolítica e extrair lentamente os serviços que foram estabelecidos pelos seus contextos vinculados no seu próprio conjunto de microsserviços. Os microsserviços podem expor uma interface RESTful para a camada da aplicação interagir, através do gateway de API, com código cola implementado para comunicar com o monólito em circunstâncias específicas.

Utilizar camada de API

À medida que continua a descascar o monólito, eventualmente chegará o ponto em que já não precisa de existir, e os microsserviços foram extraídos com sucesso do monólito. Neste momento, a camada anti-corrupção (código cola) pode ser removida com segurança.

Esta abordagem é um exemplo do padrão De Figo estrangulador e permite uma decomposição controlada de um monólito num conjunto de microsserviços. Ao longo do tempo, à medida que a funcionalidade existente é movida para microsserviços, o monólito diminuirá em tamanho e complexidade, ao ponto de já não existir.

Contribuidores

Este artigo é mantido pela Microsoft. Foi originalmente escrito pelos seguintes contribuidores.

Autor principal:

Para ver perfis do LinkedIn não públicos, inicie sessão no LinkedIn.

Passos seguintes

Quando a aplicação tiver sido decomposta em microsserviços constituintes, torna-se possível utilizar ferramentas de orquestração modernas, como o Azure DevOps , para gerir o ciclo de vida de cada serviço. Para obter mais informações, veja CI/CD para arquiteturas de microsserviços.