A Secure and Reliable Document Management System is Essential.docx
A CQRS Journey
1. A CQRS journey
An introduction to Hexagonal Software Architectural Patterns,
DDD & CQRS
2.
3. Who are we?
Thanos Nokas
Software Engineer
Human Factor
Thanos Korakas
Web Developer
Human Factor
Sotiris Gkanouris
Engineering Manager
MessageBird
Chrysovalantis Koutsoumpos
Software Engineer
6. Disclaimer
This presentation targets a broader audience and means to be
seniority/experience agnostic.
Its aim is to make a simple introduction to complex architectures providing with
enough information to get started with them.
Many structures, elements and steps are stripped in favour of simplicity.
It is build with a step-by-step approach, in a way that everyone can follow.
7. Software Architecture
● Fundamental structural choices
● Elements inside those structures
● Properties of the elements
● Responsibility of each element
● Relations between elements
● Constraints between structures and elements
“The way that we are
organizing our project’s
structure and establishing
communication between its
elements”
8. Architectural Patterns
● Reusable solution to a commonly occurring problem
● With focus on
○ performance
○ code quality
○ code reusability
○ infrastructure limitations,
○ high availability
○ minimization of a business risk
○ security
● Similar with (code) design patterns but with a broader scope
“An already proven set of
predefined structural, relation
and constraint choices”
9. Software architecture chronicles
● 50s: Non structured programming
● 60s: Structured programming
○ Tier 1
● 1979: Procedural / Functional programming
○ Model View Controller (MVC)
● 80s: Object oriented programming
○ Tier 2
● 1997: Web services, ESB
● 2003: Domain Driven Design (DDD)
● 2005: Hexagonal (AKA Ports & Adapters)
● 2006: Command Query Responsibility Segregation (CQRS), Event Sourcing
● 2008: Onion
● 2009: Microservices
● 2012: Clean
A software project may use a combination of more than one architectural patterns
12. Ports, adapters & adaptees
● A target is an object that we want to
● communicate with
● A port is an entry point. It defines a set of
functions.
● An adapter is a bridge between the application
and the service that is needed by the
application. It fits a specific port.
● An adaptee the element that uses an adapter
to communicate with a port.
● Think of your phone charger
○ Your phone is the Adaptee
○ The USB Adapter is the ...Adapter
○ The socket is the Target and it’s facade is Port
GoF - Adapter Pattern
13. use case
use case
Ports & Adapters
Message Broker
Adapter
Persistence
Adapter
Adapter
Adaptee
HTTP
use case
Port
Adaptee
Adaptee
Adaptee
Adapter
Adapter
Adapter
Port
inside
application
and
business
logic
outside
Infrastructure
outside
UI
HTTP Adapter
CLI Adapter
> CLI
DB
Message Broker
UI & Infrastructure abstractions
Port
use case
Port
14. 2008 - Jeffrey Palermo
inside
application
and
business
logic
outside
UI and
Infrastructure
outside
UI and
Infrastructure
15. Onion architecture
Domain Model
Application Services
UI / Infrastructure
2008 - Jeffrey Palermo
Domain Services
Dependency goes inwards
Outer layers depend on inner layers
Inner layers do not know about outer layers
16. Domain, Application, API, UI and Infrastructure
● Domain Model Layer — Contains all business logic, the Entities, Events and any other object type that contains Business Logic
● Application Services Layer — Orchestrates Domain objects to perform tasks required by the end users
● User Interface Layer — Displays some data to end users and where end users interact with the system
● Infrastructure Layer — Technical capabilities that support the layers above, e.g. persistence or messaging
20. Domain Model
Application Services
UI / Infrastructure
Domain Services
Onion, a superset of Hexagonal
The evolution of Ports & Adapters
DB
Message Broker
HTTP
> CLI
21. Driving / Driven Adapters
Message
Broker
Adapter
Persistence
Adapter
Secondary/
Driven Port
Port
Port
PortPort
Primary /
Driving Adapter
Secondary/
Driven Adapter
Domain
Application
UI / Infrastructure
Webport
CLIport
Messagingport
Persistenceport
HTTP
> CLI DB
Message Broker
CLI Adapter
HTTPAdapter
Primary /
Driving Port
24. (via the same)
Application
Application
Driven Adapter
(Infrastructure)
DB
Driving Adapter
(UI)
The separation of read and write flows
one way
Write flow
Two way
Read flow
Write Domain
GUI
Read Domain
25. What is CQRS
● An architectural pattern that dictates the separation of read and write flows
● 1997: Bertrand Meyer first wrote about command query separation "Object Oriented Software
Construction”
● 2006: Greg Young came up with “CQRS”
○ Definition: “Uses a different model to update information than the model you use to read
information”
○ Opinion: You do not need two models! You only need one write model (source of truth).
Query just loads a projection from the data persistence layer (DB) through a repository.
● Usually met on enterprise world
● Stands for Command Query Responsibility Segregation
26. CQRS: Why I should use it?
● Performant read/write ops
● Infrastructure separation
● Scalability
● Enforce ground rules easier
● Testability
● Easier scaffolding around it
● Ideal when having multiple representations of the same data
● Cleaner and more Comprehensive API routes
● Fits amazingly well Event Sourcing
27. CQRS: Why I should avoid it?
● You will have to embrace eventual consistency
● Increased code complexity
● Increased complexity when synchronous requests
● Need experienced team or people with potential and appetite to read and learn
● Invest a little bit more on training, probably have to pay for some consultation
● Can cause some rework until you fully understand the patterns
28. What is eventual consistency
● The state of the object is not updated instantly in all read sources
● Eventually and if no errors, the object state will be updated
● Appears in everyday life
● Other types of consistency are:
○ strong
○ weak
30. Is that all?
● Advanced layer decoupling
● REST “Alternatives”
● Never lose any data
● How to be synchronous
31. Should I use CQRS?
● Introduce it when a simple CRUD setup is not enough.
● Don’t go crazy! Take a stepped approach in order to feel comfortable.
● Avoid big refactorings or even worst rewritings.
● Complexity is increased but doable. You are getting a lot more in return.
● Keep in mind that increased complexity starts when you deal with distributed services and you have to deal with
eventual consistency.
32. Sources
● Domain-driven design Book by Eric Evans
● Implementing Domain-Driven Design Book by Vaughn Vernon
● From CQS to CQRS Article by Herberto Graca (https://herbertograca.com/2017/10/19/from-cqs-to-cqrs/)
● The software architecture chronicles Article by Herberto Graca
(https://herbertograca.com/2017/07/03/the-software-architecture-chronicles/amp)
● CQRS Article by Martin Fowler (https://martinfowler.com/bliki/CQRS.html)
● When, Why, and How to CQRS (https://www.youtube.com/watch?v=uTCKzPg0Uak)
● RabbitMq documentation (https://www.rabbitmq.com/tutorials/tutorial-six-python.html)
● Microsoft documentation (https://docs.microsoft.com/en-us/azure/architecture/patterns/cqrs)
● Hexagonal architecture demystified article by Zvonimir Spajic
(https://madewithlove.be/hexagonal-architecture-demystified/)
33. God it is over
Hopefully you made it until here
Thanks,
V