Denormalization does not eliminate the need for transactions
Most applications denormalize data to improve Data Locality and avoid running performance-intensive queries in real-time.
Read Models are a convenient mechanism to manage denormalized data. Traditionally, denormalized data structures have been held in schemaless databases because Document data models have excellent data locality. That has led to an incorrect assumption that denormalization obviates the need for transactions.
Transactions are a necessity for most applications, though not for the reasons that most developers assume. Most applications want atomic transaction support only to ensure data is persisted before sending responding to a data change request. But this is a myopic view - Returning data that was just persisted is now an anti-pattern.
Instead, most applications need support for at least Read Committed Isolation, to ensure conceptual sanctity of data. Read-Committed Isolation prevents dirty reads and dirty writes. Dirty reads confuse end-users and cause other transactions to make incorrect decisions based on the system state. Dirty writes can end up corrupting data because transactions may end up overwriting each other's changes before being committed.
If developers have ensured that Read Models hold autonomous data and Read Models store ready-to-ship information, the concern about dirty reads and dirty writes is somewhat reduced. Still, if an external system (like a User Interface) consumes data from multiple read models, then all associated read models must be updated within a single transaction. Otherwise, one read model may contain updated data while the other read model may still return old data, confusing the users.
Also, Multiple read models can be derived from the same data point. In this case, applications using different read models in other parts of the system may still show inconsistent data until all read models are synced. Eventual Consistency solves the problem mostly, but it is essential to know such possibilities exist.
It is crucial to think about data boundaries in the user interface and business functionality to build a system that does not need transactions. Read models are best constructed to align with these boundaries specified within Bounded Contexts.