Full Stack • Java • System Design • Cloud • AI Engineering

CQRS (Command Query Responsibility Segregation) Pattern in Java

Learn CQRS Pattern in Java with command and query separation, event-driven architecture, microservices, Kafka integration, Spring Boot implementation, enterprise banking examples, and interview questions.

What You Will Learn

  • What is CQRS?
  • Why CQRS is Needed
  • Commands vs Queries
  • CQRS Architecture
  • Event Driven CQRS
  • Kafka Integration
  • Spring Boot Implementation
  • Banking Examples
  • Enterprise Use Cases
  • Benefits and Limitations
  • Interview Questions

Introduction

Most traditional applications use the same model for:

Create Data

Read Data

Update Data

Delete Data

Example:

Customer Service

↓

Customer Table

↓

All Operations

Single model handles:

Reads

Writes

Problems:

Performance Bottlenecks

Scaling Issues

Complex Queries

Heavy Write Operations

CQRS solves these problems.


What is CQRS?

CQRS stands for:

Command Query Responsibility Segregation

Introduced by:

Greg Young

CQRS separates:

Commands

and

Queries

into independent models.


Purpose of CQRS

Primary Goal:

Separate

Read Operations

From

Write Operations

Traditional Architecture

flowchart LR
    A[Client]
    B[Application]
    C[Database]

    A --> B
    B --> C

Same model handles everything.


CQRS Architecture

flowchart LR
    A[Client]

    B[Command Side]

    C[Query Side]

    D[Write Database]

    E[Read Database]

    A --> B
    A --> C

    B --> D
    C --> E

Read and Write are separated.


What is a Command?

Command changes system state.

Examples:

Create Order

Update Customer

Transfer Money

Approve Claim

Commands:

Modify Data

Command Characteristics

Changes State

No Return Data

Business Validation

Transactional

Command Examples

CreateOrderCommand

UpdateCustomerCommand

TransferFundsCommand

What is a Query?

Query retrieves data.

Examples:

Get Customer

Get Orders

Get Account Balance

Get Claim Status

Queries:

Do Not Change State

Query Characteristics

Read Only

No Side Effects

Optimized For Performance

CQRS Core Idea

flowchart LR

A[Command]

B[Write Model]

C[Database]

D[Read Model]

E[Query]

A --> B
B --> C

C --> D
D --> E

Command Side

Responsible for:

Validation

Business Rules

Transactions

Persistence

Query Side

Responsible for:

Fast Reads

Reporting

Dashboards

Analytics

Banking Example

Fund Transfer System.

Commands:

Transfer Money

Create Account

Close Account

Queries:

Get Balance

Get Statement

Get Transactions

Banking CQRS Architecture

flowchart LR

A[Customer]

B[Transfer Command]

C[Account Database]

D[Balance Query]

E[Read Database]

A --> B
B --> C

A --> D
D --> E

Why Not Use One Database?

Problem:

Millions Of Reads

Thousands Of Writes

Read workload dominates.

CQRS allows:

Optimized Read Database

Optimized Write Database

E-Commerce Example

Commands:

Place Order

Cancel Order

Update Product

Queries:

Search Products

View Orders

Product Recommendations

E-Commerce Flow

flowchart LR

A[Order Command]

B[Write DB]

C[Event]

D[Read DB]

E[Product Query]

A --> B
B --> C
C --> D
D --> E

Event Driven CQRS

CQRS is commonly used with:

Event Driven Architecture

Workflow:

Command

↓

Write Database

↓

Publish Event

↓

Update Read Database

Event Driven Flow

flowchart LR

A[Command]

B[Write Database]

C[Event Bus]

D[Read Database]

A --> B
B --> C
C --> D

Kafka Based CQRS

Commands update:

Primary Database

Events published to:

Kafka

Consumers update:

Read Database

Kafka CQRS Architecture

flowchart LR

A[Order Service]

B[Write DB]

C[Kafka Topic]

D[Read Model Service]

E[Read DB]

A --> B
B --> C
C --> D
D --> E

Spring Boot Command Example

Command Object

public record CreateOrderCommand(
        String customerId,
        Double amount) {
}

Command Handler

@Service
public class OrderCommandService {

    public void createOrder(
            CreateOrderCommand command) {

        // Validate

        // Save

        // Publish Event
    }
}

Query Example

@Service
public class OrderQueryService {

    public OrderDTO getOrder(
            Long id) {

        return repository.findById(id);
    }
}

Service Separation

flowchart LR

A[OrderCommandService]

B[Write DB]

C[OrderQueryService]

D[Read DB]

A --> B
C --> D

Read Model Optimization

Read database may contain:

Denormalized Tables

Aggregated Data

Materialized Views

For faster queries.


Example Read Model

Instead of:

10 Tables Join

Use:

CustomerOrderSummary

Single table.


Read Model Flow

flowchart LR

A[Orders]

B[Customers]

C[Products]

D[Summary Table]

A --> D
B --> D
C --> D

Insurance Example

Commands:

Submit Claim

Approve Claim

Reject Claim

Queries:

Get Claim Status

View Claims

Generate Reports

Insurance Architecture

flowchart LR

A[Claim Commands]

B[Write DB]

C[Claim Queries]

D[Read DB]

A --> B
C --> D

Benefits Of CQRS

✅ Independent Scaling

✅ Faster Reads

✅ Better Performance

✅ Event Driven Friendly

✅ Supports Microservices

✅ Better Separation Of Concerns


Limitations

❌ Increased Complexity

❌ More Infrastructure

❌ Eventual Consistency

❌ More Databases

❌ Harder Debugging


Eventual Consistency

In CQRS:

Write DB Updated

Read DB Updates Later

Temporary delay may occur.


Consistency Flow

flowchart LR

A[Write Database]

B[Event]

C[Read Database]

A --> B
B --> C

CQRS vs Traditional CRUD

Feature Traditional CQRS
Read Model Same Separate
Write Model Same Separate
Scaling Difficult Easy
Complexity Low High
Performance Medium High

CQRS vs Event Sourcing

Feature CQRS Event Sourcing
Read/Write Separation Yes Optional
Stores Events No Yes
Common Together Yes Yes

Enterprise Use Cases

Banking

Fund Transfers

Account Management

Transaction History

Insurance

Claim Processing

Policy Management

Retail

Order Management

Inventory Tracking

Trading Platforms

Stock Orders

Portfolio Queries

Healthcare

Patient Records

Appointment Queries

Real Enterprise Architecture

flowchart LR

A[Client]

B[API Gateway]

C[Command Service]

D[Query Service]

E[Write Database]

F[Kafka]

G[Read Database]

A --> B

B --> C
B --> D

C --> E
E --> F
F --> G

D --> G

When To Use CQRS

Use CQRS when:

Heavy Read Traffic

Complex Reporting

Event Driven Systems

Large Scale Microservices

Separate Scaling Needed

When NOT To Use CQRS

Avoid CQRS when:

Simple CRUD Applications

Small Projects

Low Traffic Systems

Minimal Business Logic

Interview Questions

What is CQRS?

CQRS separates read operations from write operations.


What is a Command?

An operation that changes system state.


What is a Query?

An operation that retrieves data without modifying state.


Why Use CQRS?

To improve scalability and performance.


Is CQRS Same As Event Sourcing?

No.

CQRS separates reads and writes.

Event Sourcing stores events.


Can CQRS Work Without Kafka?

Yes.

Kafka is commonly used but not required.


Main Drawback?

System complexity and eventual consistency.


Key Takeaways

  • CQRS stands for Command Query Responsibility Segregation.
  • Separates Read and Write operations.
  • Improves scalability and performance.
  • Frequently used with Kafka and Event Driven Architecture.
  • Enables independent scaling of read and write workloads.
  • Common in Banking, Insurance, Retail, Trading, and Microservices platforms.
  • One of the most important modern system design patterns.