In a nutshell: What are DDD and CQRS (Domain Driven Design and Command Query Responsibility Segregation)?

Steve Mostafa Dafer
9 min readJan 2, 2023

--

Here goes the second “In a nutshell” post, even though I have to admit this is going to be a little longer than a 2 min read. But I’ll divide it into sections so that you can easily navigate through it.

DDD can stand for both: Domain-Driven Design and Data-Driven Design, even though they are two distinct approaches to software development that have different goals and focus on different aspects of the development process.

In this article, we’ll only refer to Domain-driven design by DDD.

Domain-Driven Design (DDD) is a software development approach that involves close collaboration between developers and domain experts to design a system that accurately reflects the business domain and meets the needs of stakeholders. It emphasizes the use of a common language and set of principles to understand and model the problem domain. The goal is to design software that is well-suited for the business domain it will be used in.

Bounded Contexts [src: Martin Fowler]

To support the modeling and design of complex business domains, DDD introduces a number of concepts and techniques, such as domain models, bounded contexts, and context maps. These concepts and techniques help developers understand the structure and relationships within the business domain and design a software system that accurately reflects this structure and these relationships.

Remember how that one time you modeled the DB with the gift entity, but at some point the API devs decided to use it for box since the concept changed a little bit. At some other point, another change happened, and the UI changed the name of box/gift to package but changing all references in the API and the DB was a lot of unnecessary work, so you ended up translating the package from the frontend to box in the backend, to gift in the database! Well this is exactly why defining the language/keywords based on the domain is so important! Next time you mention gift in a meeting, you’ll not end up with different people thinking about different things!

Defining the language/keywords based on the business domain [src: Golo Roden]

Advantages of DDD:

  1. Improved complexity and maintainability: By bridging the gap between developers and stakeholders (domain experts), the requirements for the short and long terms become clearer, and maintaining the system on the long run therefore becomes easier as there would be less “surprise” features that require major refactoring and overloading.
  2. Improved flexibility: This goes hand in hand with the previous point. Less complexity = better flexibility. It’s easier to modify or add new functionality to the system as the business evolves, or as the needs of the stakeholders change, when such changes can be anticipated due to the prior knowledge of the business domain. (Check the disadvantages to see how this is a conflicting topic!)
  3. Improved usability: Since the software architecture reflects the business domain, developers and stakeholders share the same naming conventions and concepts, so they are better aligned, which leads to improved usability of the system.

Disadvantages of DDD:

  1. Increased development effort: Domain-driven development involves a more complex design and architecture than traditional approaches. This can be especially challenging in cases where the business domain is large or complex, or where the system is expected to evolve over time.
  2. Increased testing effort: Especially in the early stages where the system is built to cater for the future stages; because domain-driven development systems often involve complex domain models and business processes, they can be more complex to test than traditional systems.
  3. Reduced flexibility: Bare with me here, I know that this conflicts with what we mentioned in the advantages; while the system is more flexible in terms of anticipated future updates and updates within the given domain, domain-driven development can result in a system that is less flexible than a traditional system if it requires changes to the domain model or business processes.
  4. Limited focus: Domain-driven development is primarily focused on the business domain and the needs of the stakeholders, and may not consider other important aspects of the software development process, such as performance, scalability, or security. This can result in a system that meets the needs of the stakeholders but may not be optimized for other factors.
  5. Stakeholder engagement: Domain-driven development involves close collaboration with domain experts and business stakeholders, which can require significant effort and resources. This can be especially challenging in cases where the stakeholders are geographically dispersed, or where there are multiple stakeholders with conflicting needs or goals.
  6. Cultural fit: Domain-driven development requires a culture of collaboration and shared understanding between developers and domain experts, which may not be present in all organizations.
  7. Limited applicability: Domain-driven development is most suitable for complex, business-critical systems where it is important to carefully model and design the system to meet the needs of the business. It may not be the best approach for simpler systems or systems that do not involve a complex business domain.

While I have listed more disadvantages than advantages, quality wins over quantity in this case; DDD definitely has a very solid proposal, and it does live up to the expectations, but careful study is required before going with a specific approach for any given potential solution.

If this is still confusing, don’t worry, I’ll include excellent follow-up material for you at the end; but I’m trying to keep this post “in a nutshell” as much as possible.

So now that we’ve got the concept of DDD, what is CQRS? And why are they usually used together?

A CQRS Journey [src: Microsoft]

Command Query Responsibility Segregation (CQRS): an architectural pattern that separates the read and write operations of a system into separate models. In a CQRS system, the read model is optimized for querying data, while the write model is optimized for modifying data. This separation of concerns can help improve the performance, scalability, and complexity of a system.

Commands and their relevant events, as part of CQRS [src: Golo Roden]

CQRS can be especially useful in systems where the volume of read and write operations is very different, or where the read and write models have different requirements in terms of performance, scalability, or security.

A CQRS model where Read and Write APIs are separated, but using the same DB [src: Golo Roden]

To implement CQRS, developers typically use a combination of design patterns and software development techniques, such as command and query objects, mediators, and event sourcing. These techniques help enforce the separation of concerns between the read and write models and ensure that the system is designed in a way that meets the specific needs of the business.

A CQRS model where Read and Write APIs are separated, each using a different DB [src: Golo Roden]

Both DDD and CQRS are often used in the development of complex, business-critical systems where it is important to carefully model and design the system to meet the needs of the business. They can be used together or independently, depending on the specific needs and goals of the project.

Event Sourcing [src: Golo Roden]

Advantages of CQRS:

  1. Improved performance: By separating the read and write models, a CQRS system can optimize each model for its respective purpose, especially in cases where the volume of read and write operations is very different.
  2. Improved scalability: A CQRS system can scale the read and write models independently, which can make it easier to scale the system as a whole.
  3. Improved security: By separating the read and write models, a CQRS system can provide more fine-grained control over access to data. This can help improve the security of the system by limiting the ability of users to modify data and allowing only certain users or processes to write data on different levels (e.g. DB access, api access, etc…).
  4. Improved complexity and maintainability: By separating the read and write models, a CQRS system can reduce the overall complexity of the system. This can make it easier to understand and maintain the system over time.

Disadvantages of CQRS:

  1. Increased complexity: while we just mentioned this as an advantage a few seconds ago, a different kind of complexity arises; being unable to modify/delete records organically may lead to implementing some hacks with queries (e.g. calculating some metric); this is also especially true if separate databases are used for read and write APIs; leading to eventual consistency — as opposed to immediate consistency — and difficulty managing atomic operations and scalability. (Let me know in the comments section if you’d like a post on DB principles such as ACID and BASE!)
  2. Increased development effort: Implementing CQRS requires a more complex design and architecture. Note: this is not always true, depending on the framework used and the business domain.
  3. Increased testing effort: Because CQRS systems involve multiple models and often use event-driven architectures, they can be more complex to test than traditional systems.
  4. Reduced flexibility: By separating the read and write models, a CQRS system can be less flexible than a traditional system. For example, it may be more difficult to modify or add new functionality to the system if it requires changes to both the read and write models.

Overall, the advantages and disadvantages of using DDD and/or CQRS will depend on the specific needs and goals of the project. In some cases, the benefits of improved performance, scalability, and complexity may outweigh the increased development and testing effort required to implement DDD and/or CQRS. In other cases, a traditional architecture may be more suitable. It is important to carefully consider the specific needs and goals of the project and the trade-offs involved before deciding on the methodology.

Let me know in the comments if these topics interest you… Maybe we can have a post later about DDD, DDD (again, data-driven design), TDD, BDD, and whatever else ends in DD 😅

Good Watch!

First and foremost, I highly recommend this amazing talk by Golo Roden (yes go watch it now!):

Spoiler alert: he builds a full CQRS system at the end in 15 minutes only! (the last 15 minutes of the video)

Golo Roden — DDD, Event Sourcing, and CQRS — Theory and Practice

More on the architecture and performance of CQRS and event-sourcing:

Good Reads:

  • “CQRS Journey” by Microsoft is a free e-book that provides an introduction to CQRS and how it can be used to design and build scalable and flexible systems.
    [Link]
  • “CQRS and Event Sourcing” by Greg Young is a free e-book that provides a detailed introduction to CQRS and event sourcing, two related architectural patterns that are often used in conjunction with CQRS.
    [Link]
  • “Domain-Driven Design: Tackling Complexity in the Heart of Software” by Eric Evans is a classic book on DDD that provides a comprehensive introduction to the concepts and techniques of DDD.
  • “Implementing Domain-Driven Design” by Vaughn Vernon is a practical guide to implementing DDD in software development projects. It provides concrete examples and guidance on how to apply the principles and techniques of DDD in practice.
  • “Designing Event-Driven Systems” by Ben Stopford is a book that provides a comprehensive overview of event-driven architecture and how it can be used to design scalable and resilient systems. Event-driven architecture is often used in conjunction with CQRS to implement event sourcing and other related patterns.

Written with the help of Chat GPT provided by OpenAI. With love! Thanks to Mahmoud Dafer for proof reading this post! Salam (Peace)!

--

--

Steve Mostafa Dafer
Steve Mostafa Dafer

Written by Steve Mostafa Dafer

Coffee lover, team lead, speaker, mentor, tinkerer, teacher, and engineer! https://www.linkedin.com/in/stevedafer/

Responses (3)