Bounded Contexts de dependência mútua

os Bounded Contexts de dependência mútua representam um desafio significativo na arquitetura de sistemas baseados em DDD. A necessidade de compartilhar lógica, dados e estruturas entre contextos distintos exige um cuidado especial na definição e na implementação desses padrões de relacionamento. É essencial que os arquitetos e desenvolvedores compreendam bem os princípios do DDD e busquem sempre a clareza e a coesão em seus designs para evitar armadilhas comuns que levem a inconsistência de dados, conceitos ou intenções.

No arquitetura de software, o Domain-Driven Design (DDD) se destaca como uma abordagem fundamental para estruturar sistemas complexos de forma eficaz. Um dos conceitos centrais do DDD é o Bounded Context (Contexto Delimitado), que define limites claros e isolados dentro de um sistema, permitindo a separação de responsabilidades e a modelagem mais precisa do domínio. Dentro desse contexto, surgem diferentes tipos de relacionamentos entre os Bounded Contexts. A dependência mútua será melhor explorada aqui no artigo Bounded Contexts de dependência mútua.

Aqui no blog temos muitos artigos, sendo algumas dezenas voltadas para o Domain Driven Design, como esse. Fique a vontade para explorar artigos como DDD Estratégico, DDD Tático entre outros.

Bounded Contexts de dependência mútua e os demais tipos

Uma empresa lida com diferentes estruturas para entregar valor para seu cliente. O Domain Driven Design cria o conceito de domínios, que representa em alto nível tais estruturas. Por exemplo, um banco pode ter um setor de empréstimos, outro de investimentos, outro de saques e depósitos, etc.

Entretanto, num nível mais especializado notamos que existem processos de negócio que geram efetivamente o valor ao cliente, explicitando funcionalidades, formas de interação, dados e transformações, etc. O Domain Driven Design cria então outro conceito chamado Bounded Context (Contexto delimitado em pt-br). Esse conceito define estruturas menores que funcionam internamente em domínios, podendo em alguns casos vazar de um domínio para outro.

Tipos de relação

Pois bem, contextos se relecionam de formas diferentes. Em algumas literaturas vemos que há 3 grandes tipos de relações: 1 – relação de dependência mútua; 2 – relação upstream-downstream e; 3 – relação livre. Esse artigo vai se especializar no primeiro caso.

Padrões de bounded contexts

Bom, para que tenhamos uma ideia completa do que estamos falando, há literaturas indicando a existência de 9 diferentes padrões de contexto. Eric Evans, autor do conceito, não considera todos esses, porém ele dá margem para interpretações ou mesmo evoluções.

1 – Open-host Service

2 – Conformist

3 – Anticorruption Layer

4 – Shared Kernel

5 – Partnership (não é considerado pelo Eric Evans no seu clássico livro azul)

6 – Customer / Supplier Development

7 – Published Language

8 – Separate Ways

9 – Big Ball Of Mud (também não é considerado pelo Eric Evans no seu clássico livro azul)

Padrões de Dependência Mútua

Esses padrões lidam com cenários onde dois ou mais contextos se relacionam: dependendo uns dos outros ao mesmo tempo que não há nível de poder elevado entre eles. Devemos levar em consideração que não estamos falando apenas de código ou desenvolvimento, ou seja, contextos não são apenas separações entre camadas, componentes ou microsserviços. Um contexto é, ao mesmo tempo, uma forma de organizar o negócio, modelos, códigos e dados. A imagem a seguir ajuda a entender tudo o que significa os diferentes contextos quando há dependência mútua.

Bounded Contexts de dependência mútua: Diferentes áreas de negócio na relação

Precisamos entender que há dois possíveis padrões que se encaixam no tipo de relação de dependência mútua: Shared Kernel (Núcleo Compartilhado) ou Partnership (Parceria). Ambos são bem parecidos, mas há um núcleo compartilhado quando há atividades, lógicas, dados, etc. comuns aos dois ou mais contextos envolvidos. Nesse caso ambos os lados precisam juntos decidir as ações a serem feitas. No caso do Partnership não há uma estrutura compartilhada: ambos apenas se dependem e por acordo cooperam entre si.

Entenda que um modelo desse se adequa melhor em empresas grandes, mas não há nenhuma restrição. Em muitos casos estamos falando de times distintos da operação da empresa. Então, não é raro que algumas pessoas sejam destacadas de ambos os times para trabalhar juntos quando há alterações nas áreas ou no núcleo compartilhado. Dessa forma, com esta estrutura matricial, as informações fluem entre as diferentes áreas de negócio mais facilmente.

Contexto e Modelo

No Domain Driven Design há o conceito de linguagem ubíqua. Ele indica que a maneira em que os especialistas do negócio se comunicam, bem como o modelo desenhado em diagramas, a conversa dos desenvolvedores e o código: devem estar claros para todos. Mas note que contextos diferentes podem ter modelos diferentes e, portanto, linguagens ubíquas diferentes.

Veja que os contextos devem ter modelos próprios e o núcleo compartilhado (se houver) pode ter conceitos e intenções comuns a eles. Isso deve ser pensado e realmente desejado pelos arquitetos de sistema.

Além disso, os contextos podem estar todos num só domínio, em domínios separados ou parte em um, parte em outro. Nesse sentido não podemos esquecer que diferentes domínios podem envolver diferentes áreas da direção da empresa e criar potenciais desequilíbrios políticos. Isto também deve ser visto com cuidado de modo a aproveitar oportunidades que essas situações podem trazer.

Lógicas e codificação

Muitos pensam o DDD apenas do ponto de vista da codificação, mas isto é, sem dúvida, parte secundária. Eric Evans comentou que se ele tivesse que reescrever o livro dele, ele daria mais destaque à linguagem ubiqua. De todo modo, a codificação é certamente muito importante.

A codificação pode ser feita de muitas formas distintas. Vamos a algumas possibilidades:

  • Ambos trabalhando com todo acoplado, com modelos para o contexto A, para o contexto B e para a relação A-B juntos.
  • Ambos com códigos próprios que utilizam dependências comuns. Já essas dependências são alteradas pelos dois times quando necessário.
  • Alterações nos sistemas geram eventos de domínio que são disparados através de sistemas de mensageria e fila que geram maior desacoplamento, embora ainda seja necessária comunicação e alinhamento entre os times.

Quando não há um núcleo compartilhado, ou seja, estamos falando de uma parceria, é impotante que os líderes, PO’s etc. se alinhem para que funcionalidades desenvolvidas não os atrapalhem mutuamente.

Por fim temos a integração contínua. A implantação em produção dos sistemas precisa ser cuidadosamente confeccionada ao mesmo tempo que ambos evoluem independentente.

Dados e estrutura de dados

Indo ao nível mais microscópico dessa questão temos as estruturas de dados e os dados propriamente ditos. As estruturas tendem ser independentes, ou seja, um banco para cada um, mas cada cenário é único. De todo modo é possível que haja uma pequena estrutura que seja comum. Ela pode ser replicada nos diferentes contextos e suportar um certo nível de consistência eventual. Ou ela pode efetivamente ser comum a ambos, limitando o crescimento e gerando problemas de escalabilidade. Como esse tipo de arquitetura é feita para sistemas e empresas grandes, essa não me parece ser uma boa estratégia.

Já o deployment das alterações das estruturas de dados precisam ser muito bem coordenadas com os degraus já citados: usuários do negócio, membros de ambos os contextos, desenvolvedores e, dessa vez, com o time de dados. Veja que esses dados devem desembocar numa outra fase onde relatórios analíticos são construídos. Os engenheiros de dados precisam saber claramemente onde estão os dados, quais as estruturas mais adequadas para injeri-los do melhor modo e no tempo certo.

Conclusão de Bounded Contexts de dependência mútua

Em suma, os Bounded Contexts de dependência mútua representam um desafio significativo na arquitetura de sistemas baseados em DDD. A necessidade de compartilhar lógica, dados e estruturas entre contextos distintos exige um cuidado especial na definição e na implementação desses padrões de relacionamento. É essencial que os arquitetos e desenvolvedores compreendam bem os princípios do DDD e busquem sempre a clareza e a coesão em seus designs para evitar armadilhas comuns que levem a inconsistência de dados, conceitos ou intenções.


Thiago Anselme
Thiago Anselme - Gerente de TI - Arquiteto de Soluções

Ele atua/atuou como Dev Full Stack C# .NET / Angular / Kubernetes e afins. Ele possui certificações Microsoft MCTS (6x), MCPD em Web, ITIL v3 e CKAD (Kubernetes) . Thiago é apaixonado por tecnologia, entusiasta de TI desde a infância bem como amante de aprendizado contínuo.