https://www.techtarget.com/searchapparchitecture/definition/CQRS-command-query-responsibility-segregation
CQRS (command query responsibility segregation) is a programming design and architectural pattern that treats retrieving data and changing data differently. CQRS uses command handlers to simplify the query process and hide complex, multisystem changes.
When the CQRS pattern is combined with the event sourcing pattern, it guarantees an audit log of changes to the database that can help maintain transactional consistency. Moreover, its read model can contain, or be used to generate, a materialized view pattern of write model data.
CQRS is a software architecture pattern in which the responsibilities of a system's commands and queries are segregated by vertically slicing the application logic. You can think of the pattern as a way to separate read and update operations for a data store. The goal of CQRS is maximizing application performance, security and scalability.
In CQRS, a command conveys the user's intent. It is an instruction the user provides to the system to perform a certain task. A command does not generate a result and is part of the write model. A query is a user's request for information. It returns a result but does not change the state and is part of the read model.
Greg Young developed the CQRS design pattern in 2010, around the same time as event sourcing emerged. As he defined the pattern: "[CQRS] uses the same definition of commands and queries that Meyer used and maintains the viewpoint that they should be pure. The fundamental difference is that, in CQRS, objects are split into two objects, one containing the commands, one containing the queries." Young was referring to Bertrand Meyer, who developed CQRS' predecessor, the command query separation (CQS) pattern.
Although related to and inspired by CQS, CQRS is different in that objects are split into two objects: one containing commands and one containing queries. Separate model representations for queries and commands make the approach highly suitable for event sourcing or task-based user interface (UI) applications. In contrast, the CQS application architecture pattern is mainly about separating the logic for queries that don't update a system's observable state from the logic of commands that do perform state updates.
Bertrand Meyer first referred to CQS in his book, Object-Oriented Software Construction. It is also part of his work on the Eiffel programming language. He proposed separating methods that change state from those that don't. This enables queries to be confidently used in many situations. They can also be introduced anywhere, and their order can be changed as needed.
Learn more about the most popular programming languages in the world.
The CQRS pattern is useful in all these scenarios:
It's important to consider CQRS' unique requirements and limitations and assess thoroughly whether this pattern is appropriate for its particular use cases. Use it only in restricted situations where it's necessary. It's useless for systems that follow the create, read, update and delete mental model.
The most common way to deploy CQRS is the command pattern, which is the software system that defines a high-level interface. At runtime, the base class takes the command, creates the appropriate object handler -- perhaps update, delete or create -- and calls a method to execute the command.
Before and after execution, the base class can log that the method was called. The log can be replayed from and to any point in time. Once the interface and dispatch code exist, the computer program to take the events and replay them is called a for loop. It reads a file from a certain point, and then, for each line, it calls the command on that line with the data on that line. The complexity hidden inside the command handler is limited or encapsulated by the handler.
The handlers call each step of the process to create, update or delete a logical item in the system. They can dispatch the first request and monitor to see when that action completes, handling errors and rollbacks if needed. The handler sets up a long-running, two-phase commit (saga pattern) post in which it writes the results to the event log. This log contains a record of every system change. If this log is created in a consistent way that a program can read and replay, it enables event sourcing.
When a customer looks at an order, a straightforward process is executed: a read from a database. The read could be from a NoSQL key-value store, like Redis, that stores all customer information. A microservice picks up the information, and a webpage displays it. The Redis team, working with the front-end developers, can handle the read side easily.
The operation's write side is much more complex and contains several different steps and dependencies. For example, if an order is canceled before it is shipped, the following occurs:
Since a single change (order cancellation) must be copied to so many places, the update, delete and create sides of the operation must interact with either an enterprise service bus (ESB)or a command handler, such as the saga pattern. CQRS helps create the logic to handle these complex transactions.
Some challenges associated with CQRS are the following:
The CQRS pattern is frequently used with the event sourcing pattern. The latter is an approach to a series or sequence of events. Events are user-generated actions, such as clicking a mouse button or pressing a keyboard key. CQRS-based systems use separate read/write data models, where each model is tailored to relevant tasks and often located in physically separate data stores.
In CQRS, the system tracks past changes in data states and alerts users on how to handle them. Every step of the data transformation process is recorded, not just the most recent state. Since the system itself can be recreated as the collection of all the changes over time, it creates a new view of data in the system: the transaction log. This log is not just a text file, but an actual set of commands that can be replayed to recreate the change. In some cases, the event log can be "played backward" to undo large changes.
Setting up event sourcing requires capturing the changes, along with building the software to replay those changes. Deployed carefully, command handlers can write to a log, creating the transaction log for event sourcing. Running each line in the log through a command handler executes event sourcing.
The CQRS and event sourcing patterns have considerable overlap. The command in CQRS is one way to create event sourcing. CQRS works well with event sourcing since it divides the system by business operations and events are the result of those operations.
CQRS is compatible with domain-driven design -- an explicit domain model -- event sourcing and the command pattern. An ESB might deliver the messages to perform the create, update and delete. The general pattern is service-oriented architecture.
While CQRS can be useful in constructing an event-driven architecture, bad practices can turn it into more of a nuisance. Explore common CQRS pattern problems, and see how they can be mitigated.
31 May 2024