When developers begin exploring scalable architecture patterns in .NET, two concepts often appear side by side: CQRS (Command Query Responsibility Segregation) and MediatR. It’s easy to assume they’re the same — or that one depends on the other. But let’s get this straight:
In this article, we’ll break down what CQRS truly means, how MediatR fits into the picture (if at all), and show real-world examples so you can apply the right concept at the right time.
What is CQRS?
CQRS (Command Query Responsibility Segregation) is a design pattern that separates read and write operations in your system.
In Simple Terms
Command: Changes the system state (Create, Update, Delete).
Query: Retrieves data (Read-only operations).
The idea is to decouple how you handle commands from how you handle queries, potentially allowing different models, teams, or even databases for each.
Example of CQRS (Without MediatR)
// Command
public class CreateOrderCommand
{
public string ProductId { get; set; }
public int Quantity { get; set; }
}
// Command Handler
public class OrderCommandHandler
{
public void Handle(CreateOrderCommand command)
{
// Validate and create order
}
}
// Query
public class GetOrderByIdQuery
{
public Guid OrderId { get; set; }
}
// Query Handler
public class OrderQueryHandler
{
public OrderDto Handle(GetOrderByIdQuery query)
{
// Fetch and return order from DB
}
}
Key Points
CQRS is about the separation of concerns, not about what library you use.
It can be implemented with or without MediatR.
What is MediatR?
MediatR is a simple .NET library by Jimmy Bogard that helps implement the mediator pattern. It allows sending messages (commands, queries, notifications) without directly referencing the handler.
In Simple Terms
Example of MediatR
// Command
public class CreateOrderCommand : IRequest
{
public string ProductId { get; set; }
public int Quantity { get; set; }
}
// Command Handler
public class CreateOrderHandler : IRequestHandler<CreateOrderCommand>
{
public Task Handle(CreateOrderCommand request, CancellationToken cancellationToken)
{
// Handle logic here
return Task.CompletedTask;
}
}
// Usage
await _mediator.Send(new CreateOrderCommand { ProductId = "P001", Quantity = 2 });
Why CQRS ≠ MediatR
While MediatR is commonly used in CQRS implementations, especially in .NET apps, it’s not a requirement.
You could
Think of MediatR as a tool in your CQRS toolbox — not the definition of it.
When to Use CQRS Without MediatR
Use CQRS alone when:
You want full control over dependencies.
You don’t want extra abstraction layers.
You are in a microservice or event-driven architecture.
Use CQRS with MediatR when:
You want clean separation and minimal ceremony.
You’re building a modular monolith or large application.
You favor testability and extensibility.
Summary
CQRS is a design principle to split reads and writes.
MediatR is a messaging library that simplifies communication between components.
They are not the same , but they can work well together .