Using Domain-Driven Design When Creating Microservices
Microservices and Domain-Driven Design (DDD) are not only about Bounded contexts, although a fundamental tool for defining granularity of microservices there are other important concepts as well. Correspondingly DDD is just not about entities, value objects and repositories, Michael Plöd claimed in his presentation at the recent microXchg conference in Berlin showing how DDD can be used when creating microservices.
Plöd, Principal Consultant at innoQ, believes DDD can help in four major areas when building microservices:
- Strategic design which is mainly about Bounded context, but Context map and other patterns are also important.
- Internal building blocks, using tactical patterns like entities, aggregates and repositories when designing the internals of a bounded context.
- Large-scale structures for creating a structure using evolving order and responsibility layers.
- Distillation with ways to distil a core domain from an already grown system.
Any sophisticated business domain consists of one or more bounded contexts, each responsible for one part of the domain. A bounded context contains models describing the domain and is also a boundary for the meaning of these models. Using a customer as an example each bounded context has its own model and view of a customer and for Plöd this is a major enabler for independent microservices.
A context map shows all bounded contexts and their relation to each other and also describes the contract between them. For organisations with an existing landscape wanting to move to microservices Plöd believes that a context map may be especially useful. It can also be a great starting point for future transformations. Patterns for common types of relationships between two contexts include:
- Shared kernel meaning two contexts or models share a subset of a domain including code. Plöd notes that this also increases the dependency.
- Customer – Supplier, with one context acting as a customer asking for features from another context, the supplier.
- Anticorruption layer (ACL), where a client isolates its model from another model using a translation. This is an interesting option especially when migrating to a microservices or a Self-Contained Systems (SCS) architecture since the ACL works as a protecting shield against the outside.
Among the internal building blocks Plöd notes the special importance of the aggregate. It’s a group of domain objects handled together and with one entity the aggregate root through which all requests and responsible for the lifecycle of the aggregate.
With an inflexible architecture or if a system becomes too complex it may be helpful to create a Large-scale structure across bounded contexts and letting this structure evolve towards a better understanding of the high-level concepts. Plöd notes that this is also one the core ideas of microservices, they should be designed so that they can evolve. Responsibility layers is another structural pattern for creating an internal structure in a bounded context according to responsibilities but the concept can also be adapted structuring microservices in the same way.
Moving from a legacy system to a microservices or self-contained system architecture the use of Distillation can help in extracting microservices out of an existing monolithic system. Starting with identifying and extracting the core domain it is then an iterative work of identifying a subdomain, extracting it from the core and finally with some clean-up internal refactoring. Pödl emphasizes the importance of documenting the business capability and the details of the core domain. Without a clear vision and knowledge of the business capability the risk of not finding the optimal bounded contexts increases.
Looking at all the concepts he has described Pödl concludes by stating that microservices and DDD really fits well together but also notes that we must have a larger scope and look beyond bounded contexts.