Distillation is the process of identifying the domain, decoupling it, isolating it, clarifying it and making it explicit, allowing us to focus on what is more relevant and having it maintainable.
There are a few techniques that can be used to distil a model.
Each of these techniques requires a successively greater commitment, but a knife gets sharper as its blade is ground finer. Successive distillation of a domain model produces an asset that gives the project speed, agility, and precision of execution.
e-book loc. 6509
Going through this distillation process has several benefits:
- Makes the overall design explicit and known;
- Distinguishes what is Core Domain from what is Generic Domain, reducing them to manageable sizes;
- Focus the software evolution (development and refactoring) in what is more relevant at a given moment.
Within the Domain, the Core Domain is the actual purpose of the application, is the reason of its existence, its why we started building it in the first place.
The Core Domain is the most business critical part of the Domain.
The distillation and definition of the core domain is crucial and it should drive human resources hiring and allocation, as well as the biggest design effort to create a supple and maintainable design:
- Hire developers that fit best with the Core Domain;
- Assign the best developers to the Core Domain;
- Try your best to keep the Core Domain the priority in suppleness and maintainability;
- Refactorings that most closely affect the Core Domain should have priority;
As our knowledge of the domain grows, while we develop the application our understanding of what is the Core Domain will also change and be more refined, more accurate. This means that something we thought, in the beginning, to be part of the Core Domain might after all be a support Domain module. It also means that something that is part of the Core Domain in one application, can be part of the Support Domain in another application and have a simpler implementation.
The greatest value of custom software comes from the total control of the Core Domain.
e-book loc. 6492
This statement, made by Eric Evans, gives us a few guidelines on how to manage our team and project:
- Create long term relations with your best, most committed and interested domain experts;
- Create opportunities for our best technical experts to learn the Domain;
- Assign our best, most committed, interested and long term connected developers to develop and maintain the Core Domain;
- Use a well designed framework to save us from developing the most generic parts and leave us free to focus on the core.
Creating distinctive software comes back to a stable team accumulating specialized knowledge and crunching it into a rich model
e-book loc. 6501
Furthermore, a first version of the application should be mainly an implementation of the Core Domain (MVP), even if very simple, unless the team is very experienced and has very good knowledge of the Domain.
These Generic Sub-Domains are part of our Domain. We need them for sure, and we want to have them for granted, not think too much about it. They are important for our application, but they could be important to many other different applications as well, meaning that they are not what distinguishes our application.
An example of a Generic Sub-Domain is “time-zones”. Although time-zones are needed, and maybe even crucial, they are not part of our main business.
We need to:
- Identify cohesive Sub-Domains that are not the main motivation of our project;
- Extract those Sub-Domains into cohesive and decoupled modules;
- Consider using existing solutions (community off-the-shelve solutions).
Domain Vision Statement
The Domain Vision Statement is a short textual description of the value of a specific Domain Model. It identifies the Core Domain.
It can be derived from a Project Vision Statement, but it is more specific, it focus on the nature of the Domain Model, its value and differential.
It is a document that should be used through the whole development process, helping to guide resource allocation, guide modelling choices and educate team members.
This will help keep the team focus on what is really important in the project and the Domain at hand.
Highlighting the Core means making it evident to the team.
For this purpose we can have two approaches:
- Extensive formal documentation, using UML and other diagramming. For ex. A digital document vault;
- Reduced and informal, but visible, documentation of concepts. For ex. A context diagram, hand drawn, hanging on the office wall.
The distillation document
Eric Evans advises us to write a brief document describing the Core Domain and the interactions between its core elements.
This document should be minimalistic, should not contain implementation details, on the contrary, it should focus on abstractions, broad strokes, the stable concepts.
The flagged core
If we have a projects full specifications documentation it will, most likely, not make clear what are the key concepts of the project, and actually obfuscate concepts.
At this point, it will be necessary to go through such documentation with a domain expert and extract what are the generic domain concepts. The result should be a very concise document listing and briefly explaining the concepts.
Encapsulation is one of the main principles of O.O. Design. It’s about keeping related data and its related logic together and protected from inappropriate access.
Hiding complex algorithms in intention revealing names separates the what from the how. This technique makes a design simpler to understand and use.
e-book loc. 6760
However, keeping the “what” separated from the “how” is not as simple as it sounds. Adding features and complexity to a class can make its API bloated and blur its core interface which creates the actual problem that its supposed to solve.
To help maintainability, simplicity and usability of the Domain classes, we should extract cohesive mechanisms sets into separate libraries which can then be used by the Domain objects, through interfaces, keeping these smaller, focused and more expressive.
The CORE DOMAIN and a GENERIC SUBDOMAIN formulate facts, rules or problems.
A COHESIVE MECHANISM resolves a rule as needed by the model, and can be used as a separate library.
An example of a COHESIVE MECHANISM is a graph traversal framework which, although being a generic programming theme with many possible algorithms, implements only the traversal algorithms needed by the Domain.
Another example can be a STATE MACHINE library, which is a generic cohesive concept who’s complexity can be kept away from the Domain and used through an intention revealing interface.
Yet another example can be a library to construct SPECIFICATION objects.
Generic Subdomains Vs Cohesive Mechanisms
Both Generic Subdomains and Cohesive Mechanisms share the goal of responsibility segregation and keeping the Core Domain focused on what is more relevant in the domain.
The difference is that the Generic Subdomain is still part of the Domain, although not as important as the Core Domain, and a Cohesive Mechanism is not part of the Domain at all, it is used by the Domain to solve a very generic problem, using a set of cohesive algorithms.
Generic Subdomains reduce the clutter in the Core Domain, leaving it focused on what is more important.
Cohesive Mechanisms are used to encapsulate complex operations used by the Domain.
Choosing refactoring targets
When we find ourselves with a poorly factored application as a whole, we need to prioritize and decide on our refactoring taregets.
Eric Evans gives us two options:
- If in a “pain driven” refactoring, we need to find the root cause of the problem and start there, wherever that is.
- If in a “all out” refactoring, we need to start by refactoring the Core Domain into segregated Core Domains, Generic Subdomains and Cohesive Mechanisms.