Top Related Projects
Cecil is a library to inspect, modify and create .NET programs and libraries.
This repository contains a suite of libraries that provide facilities commonly needed when creating production-ready applications.
Assembly scanning and decoration extensions for Microsoft.Extensions.DependencyInjection
Quick Overview
MediatR is a simple, unambitious mediator implementation in .NET. It supports request/response, commands, queries, notifications, and events, using a mediator pattern to reduce dependencies between objects. MediatR helps to decouple the in-process sending of messages from handling messages.
Pros
- Simplifies application architecture by reducing direct dependencies between components
- Supports various types of messages: requests, commands, queries, and notifications
- Easy to integrate with dependency injection containers
- Lightweight and has minimal impact on performance
Cons
- Can lead to overuse, potentially complicating simple scenarios
- May introduce additional indirection, making code flow harder to follow
- Requires careful design to avoid creating a "god object" mediator
- Learning curve for developers unfamiliar with the mediator pattern
Code Examples
- Defining a request and handler:
public class PingRequest : IRequest<string> { }
public class PingHandler : IRequestHandler<PingRequest, string>
{
public Task<string> Handle(PingRequest request, CancellationToken cancellationToken)
{
return Task.FromResult("Pong");
}
}
- Sending a request:
public class SomeService
{
private readonly IMediator _mediator;
public SomeService(IMediator mediator)
{
_mediator = mediator;
}
public async Task<string> DoPing()
{
return await _mediator.Send(new PingRequest());
}
}
- Publishing a notification:
public class ProductAddedNotification : INotification
{
public int ProductId { get; set; }
}
public class EmailNotificationHandler : INotificationHandler<ProductAddedNotification>
{
public Task Handle(ProductAddedNotification notification, CancellationToken cancellationToken)
{
// Send email logic here
return Task.CompletedTask;
}
}
// Publishing the notification
await _mediator.Publish(new ProductAddedNotification { ProductId = 123 });
Getting Started
-
Install MediatR via NuGet:
dotnet add package MediatR
-
Register MediatR in your dependency injection container:
services.AddMediatR(cfg => cfg.RegisterServicesFromAssembly(typeof(Startup).Assembly));
-
Create a request and handler:
public record MyRequest(int Id) : IRequest<string>; public class MyHandler : IRequestHandler<MyRequest, string> { public Task<string> Handle(MyRequest request, CancellationToken cancellationToken) { return Task.FromResult($"Response for Id: {request.Id}"); } }
-
Use MediatR in your application:
public class MyController : ControllerBase { private readonly IMediator _mediator; public MyController(IMediator mediator) { _mediator = mediator; } public async Task<IActionResult> Get(int id) { var result = await _mediator.Send(new MyRequest(id)); return Ok(result); } }
Competitor Comparisons
Cecil is a library to inspect, modify and create .NET programs and libraries.
Pros of Cecil
- Specialized for .NET assembly manipulation and inspection
- Provides low-level access to IL code and metadata
- Widely used in tools like Mono.Linker and Unity3D
Cons of Cecil
- Steeper learning curve due to its low-level nature
- Less suitable for high-level application architecture patterns
- Requires more code to achieve common tasks compared to MediatR
Code Comparison
Cecil (assembly manipulation):
var assembly = AssemblyDefinition.ReadAssembly("MyAssembly.dll");
var type = assembly.MainModule.GetType("MyNamespace.MyClass");
var method = type.Methods.First(m => m.Name == "MyMethod");
method.Body.Instructions.Clear();
assembly.Write("ModifiedAssembly.dll");
MediatR (mediator pattern implementation):
public class MyRequest : IRequest<MyResponse> { }
public class MyHandler : IRequestHandler<MyRequest, MyResponse>
{
public Task<MyResponse> Handle(MyRequest request, CancellationToken cancellationToken)
{
// Handle the request and return a response
}
}
Cecil is focused on low-level assembly manipulation, while MediatR implements the mediator pattern for decoupling application components. Cecil is more suitable for tooling and framework development, whereas MediatR is better for structuring application logic and implementing CQRS patterns.
This repository contains a suite of libraries that provide facilities commonly needed when creating production-ready applications.
Pros of Extensions
- Broader scope, offering a wide range of utility extensions for .NET applications
- Official Microsoft support and integration with the .NET ecosystem
- Regular updates and maintenance aligned with .NET release cycles
Cons of Extensions
- Less focused on specific design patterns like mediator
- May require more setup and configuration for specific use cases
- Potentially steeper learning curve due to its broader scope
Code Comparison
MediatR:
public class PingHandler : IRequestHandler<Ping, string>
{
public Task<string> Handle(Ping request, CancellationToken cancellationToken)
{
return Task.FromResult("Pong");
}
}
Extensions (Dependency Injection):
public void ConfigureServices(IServiceCollection services)
{
services.AddTransient<IMyService, MyService>();
services.AddScoped<IAnotherService, AnotherService>();
}
While MediatR focuses on implementing the mediator pattern for decoupling request/response handling, Extensions provides a broader set of utilities, including dependency injection, logging, and configuration. MediatR offers a more specialized solution for CQRS-like architectures, while Extensions aims to enhance the overall .NET development experience with various utility extensions.
Assembly scanning and decoration extensions for Microsoft.Extensions.DependencyInjection
Pros of Scrutor
- Focuses on assembly scanning and registration of services, providing more flexibility in service registration
- Offers advanced filtering capabilities for service registration, including attribute-based filtering
- Supports convention-based registration, making it easier to register multiple services following a pattern
Cons of Scrutor
- Lacks built-in mediator pattern implementation, which MediatR provides out-of-the-box
- May require more setup and configuration compared to MediatR's simpler approach
- Does not include request/response handling or notification features
Code Comparison
Scrutor:
services.Scan(scan => scan
.FromAssemblyOf<ITransientService>()
.AddClasses(classes => classes.AssignableTo<ITransientService>())
.AsImplementedInterfaces()
.WithTransientLifetime());
MediatR:
services.AddMediatR(cfg => cfg.RegisterServicesFromAssembly(typeof(Startup).Assembly));
While Scrutor provides more granular control over service registration, MediatR offers a simpler setup for implementing the mediator pattern. Scrutor excels in scenarios requiring complex service registration logic, whereas MediatR is better suited for applications focusing on request/response handling and notifications.
Convert designs to code with AI
Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.
Try Visual CopilotREADME
MediatR
Simple mediator implementation in .NET
In-process messaging with no dependencies.
Supports request/response, commands, queries, notifications and events, synchronous and async with intelligent dispatching via C# generic variance.
Examples in the wiki.
Installing MediatR
You should install MediatR with NuGet:
Install-Package MediatR
Or via the .NET Core command line interface:
dotnet add package MediatR
Either commands, from Package Manager Console or .NET Core CLI, will download and install MediatR and all required dependencies.
Using Contracts-Only Package
To reference only the contracts for MediatR, which includes:
IRequest
(including generic variants)INotification
IStreamRequest
Add a package reference to MediatR.Contracts
This package is useful in scenarios where your MediatR contracts are in a separate assembly/project from handlers. Example scenarios include:
- API contracts
- GRPC contracts
- Blazor
Registering with IServiceCollection
MediatR supports Microsoft.Extensions.DependencyInjection.Abstractions
directly. To register various MediatR services and handlers:
services.AddMediatR(cfg => cfg.RegisterServicesFromAssemblyContaining<Startup>());
or with an assembly:
services.AddMediatR(cfg => cfg.RegisterServicesFromAssembly(typeof(Startup).Assembly));
This registers:
IMediator
as transientISender
as transientIPublisher
as transientIRequestHandler<,>
concrete implementations as transientIRequestHandler<>
concrete implementations as transientINotificationHandler<>
concrete implementations as transientIStreamRequestHandler<>
concrete implementations as transientIRequestExceptionHandler<,,>
concrete implementations as transientIRequestExceptionAction<,>)
concrete implementations as transient
This also registers open generic implementations for:
INotificationHandler<>
IRequestExceptionHandler<,,>
IRequestExceptionAction<,>
To register behaviors, stream behaviors, pre/post processors:
services.AddMediatR(cfg => {
cfg.RegisterServicesFromAssembly(typeof(Startup).Assembly);
cfg.AddBehavior<PingPongBehavior>();
cfg.AddStreamBehavior<PingPongStreamBehavior>();
cfg.AddRequestPreProcessor<PingPreProcessor>();
cfg.AddRequestPostProcessor<PingPongPostProcessor>();
cfg.AddOpenBehavior(typeof(GenericBehavior<,>));
});
With additional methods for open generics and overloads for explicit service types.
Top Related Projects
Cecil is a library to inspect, modify and create .NET programs and libraries.
This repository contains a suite of libraries that provide facilities commonly needed when creating production-ready applications.
Assembly scanning and decoration extensions for Microsoft.Extensions.DependencyInjection
Convert designs to code with AI
Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.
Try Visual Copilot