Domain Driven Design - Overview

Domain-Driven Design is an approach to software development that centers the development on programming a domain model that has a rich understanding of the processes and rules of a domain.

DDD and it's unifying principle

Every software system built has a model at its heart. If this model matches the underlying domain well, the software will accept enhancements more easily, and it has a much better chance of surviving and thriving intact for years. The model may not be obvious; it may exist only in the mind of the developers, but it exists nonetheless. Elegant designs are possible in any paradigm.

It's this alignment that matters, and achieving and maintaining alignment is the fundamental purpose of DDD.

It's a continuous process

Striving for model-domain harmony never ends, as long as the business keeps changing. That's alright, because DDD is a continuous process.

DDD philosophy

Ubiquitous Language is the term used in Domain Driven Design for the practice of building up a common, rigorous language between developers and stakeholders. This language should be based on the Domain Model used in the software - hence the need for it to be rigorous, since software doesn't cope well with ambiguity.

Using the ubiquitous language in conversations with domain experts is an important part of testing it, and hence the domain model.

This emphasis on pure definitions and unified communications, within specific boundaries, is the glue that holds it all together, the philosophical principle that keep everything else on track. The strategic, tactical, and technical aspects of DDD are intended to support and enforce this philosophy.

The strategic aspect

The strategic aspect of DDD aligns software development teams' efforts with the interests of the business. It helps when deciding what to focus on, usually by identifying one core domain. This may be a specific area of business or even a specific slice that's critical.

The tactical aspect

The tactical, technical aspect of DDD guides the implementation process with the fundamental purpose of protecting the model from corruption. The patterns and architectural structures commonly associated with DDD flow naturally from this constraint, to provide the requisite layers of protection.

Why it's hard?

In many ways, DDD is considered hard to do right: it takes a certain amount of self-discipline to adhere to the philosophy and requires another level of restraint to resist designing when you should be modeling. It also takes courage to keep asking "What does this really mean?" and "Why does this happen?" until the deeper model is uncovered.

It also requires patience to keep refining, refactoring, iterating, and accepting feedback until the model, the code, and the business coalesce into a cooperative synergy.

Do it anyway?

If you're building simple applications in a simple domain, your model will also be simple, and so shouldn't be excessively time-consuming to discover. That doesn't mean that crafting it will be easy, though. Above all, you must commit to learning about the business. You can't help the business develop its capabilities without understanding the business.

A little DDD can go a long way. Even if you decide not to continue DDD practices past the initial model, or only go for a few iterations, you'll be able to make that decision from a position of knowledge.

Classifications

In his excellent book Domain Driven Design, Eric Evans creates a classification of the different kinds of domain objects that you're likely to run into.

  • Entity: Objects that have a distinct identity that runs through time and different representations. You also hear these called "reference objects".
  • Value Object: Objects that matter only as the combination of their attributes. Two value objects with the same values for all their attributes are considered equal.
  • Service: A standalone operation within the context of your domain. A Service Object collects one or more services into an object. Typically, you will have only one instance of each service object type within your execution context.
  • Aggregate: An aggregate is a cluster of domain objects that can be treated as a single unit. An aggregate will have one of its component objects be the aggregate root. Any references from outside the aggregate should only go to the aggregate root. The root can thus ensure the integrity of the aggregate as a whole

I will write more about these domain objects in future articles and, provide code examples from a simple domain.

Before you start with DDD

Domain-Driven Developers need to be comfortable with the following:

  • Object-Oriented Programming Basics
  • Object-Oriented Programming Design Principles such as,
    • composition,
    • encapsulation,
    • inheritance,
    • referring to abstractions, and
    • SOLID Principles.
  • General Design Principles such as,
    • KISS, and
    • DRY.

Published: 2021-02-15
Author: Henrik Grönvall
Henrik Grönvall
Copyright © 2022 Henrik Grönvall Consulting AB