This week, in our study group, there is an interesting question.
If our service use MongoDB as the primary database and leverage ElasticSearch to benefit searching. Each request is in, our service is responsible for a dual write to update both MongoDB and ElasticSearch. Is this implementation considered CQRS?
In fact, this implementation is indeed generating a read model for searching and a write model for domain operations. If there is any search request, we can build a search layer or a search service for that.
This looks like CQRS, doesn't it?
In my opinion, such an implementation is not CQRS.
There are two core concepts about CQRS.
- event sourcing
- responsibility segregation
Let's see their actual meaning.
Event sourcing
Event sourcing is the most important concept for CQRS. When we have a new feature requirement, we can leverage the existed events and replay to generate a new read model so that we don't need to modify the original code base.
In other words, we can easily fulfill any query requirement without impact the production functionality.
Let's go back to the original example.
If our service keeps every input event in MongoDB so that new read models can be generated in the future, then I would say it's "very much like" CQRS.
Responsibility segregation
The another key point is the responsibility segregation, i.e., the last two letters of CQRS.
What does that mean?
From my point of view, responsibility for building the read and write models must be separated.
If our service is responsible for both update MongoDB and update ElasticSearch, that doesn't sound separate at all.
In order to release the burden of updating many models, CQRS introduces an event synchronization mechanism for event consumers to generate read models and make them consistent eventually.
Let's continue with the original example.
If our service maintain the MongoDB's domain states and keep every domain operation as audit logs. Then, we can build a worker who regularly digest these logs and update ElasticSearch. So, this is a CQRS definitely.
Conclusion
Why do we need to clarify these terminology details? Is it important to know if it is considered CQRS?
Well, it depends.
If we want to make the original system better, then we need to know exactly what a paradigm means. If we hastily assume that the original system is already a paradigm, then we miss the opportunity to look at it deeply.
The original implementation actually works well at the moment. However, if the input request increases, updating ElasticSearch will become a bottleneck while handling domain operations. At that time, we then have to make additional improvements.
Those paradigms are the indexes that provide how to improve. Because of this, we need to understand the specifics of the paradigms.