核心对象
IMediator
IRequest
、IRequest<T>
IResuestHandler<in TRequest,TResponse>
代码展示
创建名字为MediatorDemo
的控制台应用
,通过nuget
引入以下三个包:
MediatRMediatR.Extensions.Microsoft.DependencyInjectionMicrosoft.Extensions.DependencyInjection
创建命令和处理者存放路径
在根目录创建以下两个文件夹:
CommandsCommandHandlers
创建命令
在Commands
文件夹中创建MyCommand.cs
,内容如下
using MediatR;namespace mands{public class MyDemoCommand:IRequest<string>{public string Data {get; }public MyDemoCommand(string data){Data = data;}}}
创建命令处理者
在CommandHandlers
文件夹中创建MyDemoCommandHandler.cs
,内容如下:
using System.Threading;using System.Threading.Tasks;using mands;using MediatR;namespace mandHandlers{public class MyDemoCommandHandler:IRequestHandler<MyDemoCommand,string>{public async Task<string> Handle(MyDemoCommand request, CancellationToken cancellationToken){await pletedTask;return $"Hello from MyDemoCommandHandler.Handler -> command data = {request.Data}";}}}
发送命令
修改Program.cs
,具体内容如下:
using System;using System.Threading.Tasks;using mandHandlers;using MediatR;using Microsoft.Extensions.DependencyInjection;namespace MediatorDemo{class Program{static async Task Main(string[] args){var service = new ServiceCollection();service.AddMediatR(typeof(Program).Assembly);var serviceProvider = service.BuildServiceProvider();var mediator = serviceProvider.GetService<IMediator>();var rsp = await mediator.Send(new MyDemoCommand("This is my demo command"));Console.WriteLine(rsp);}}}
解释代码:
通过var service = new ServiceCollection();
创建服务容器service.AddMediatR(typeof(Program).Assembly);
是想服务容器注册MediatR
组件,同时指定MediatR
扫描当前Program
所在的程序集,获得当前程序集里的所有Command
和Handler
(通过接口约束)var mediator = serviceProvider.GetService<IMediator>();
从服务容器中获取mediator
对象var rsp = await mediator.Send(new MyDemoCommand("This is my demo command"));
发送一条MyDemoCommand
命令
运行代码
运行代码之后可以看到控制台打印以下信息:
Hello from MyDemoCommandHandler.Handler -> command data = This is my demo command
可以看到Program
并没有直接去引用MyDemoCommandHandler
这个类,只是向MediatR
发送了一条指定的命令,MediatR
框架会自动去查找该命令对应的Handler
,调用Handler
里的Handle
方法
注意:所谓一对一就是当你有对一个命令有多个Handler
的时候,MediatR
只会找到最后注册的那个来执行
一对多
核心对象
IMediator
INotification
INotificationHandler<in TNotification>
代码实现
创建事件和事件处理者存放路径
在根目录创建以下两个文件夹:
EventsEventHandlers
创建事件
在Events
文件夹中创建MyDemoEvent.cs
,内容如下:
using MediatR;namespace MediatorDemo.Events{public class MyDemoEvent:INotification{public string EventName {get; }public MyDemoEvent(string eventName){EventName = eventName;}}}
创建事件处理者
在EventHandlers
文件夹中创建MyDemoEventHandler.cs
,内容如下:
using System;using System.Threading;using System.Threading.Tasks;using MediatorDemo.Events;using MediatR;namespace MediatorDemo.EventHandlers{public class MyDemoEventHandler:INotificationHandler<MyDemoEvent>{public async Task Handle(MyDemoEvent notification, CancellationToken cancellationToken){await pletedTask;Console.WriteLine($"MyDemoEventHandler.Handle执行:{notification.EventName}");}}public class MyDemoEventHandlerV2 : INotificationHandler<MyDemoEvent>{public async Task Handle(MyDemoEvent notification, CancellationToken cancellationToken){await pletedTask;Console.WriteLine($"MyDemoEventHandlerV2.Handle执行:{notification.EventName}");}}}
这里是一个cs
文件中写了两个Handler
修改Program
在原有的Main
方法最后面添加以下代码:
await mediator.Publish(new MyDemoEvent("MyEvent"));
运行代码
运行项目可以看到以下信息:
Hello from MyDemoCommandHandler.Handler -> command data = This is my demo commandMyDemoEventHandler.Handle执行:MyEventMyDemoEventHandlerV2.Handle执行:MyEvent
其中后面两行分别为两个事件处理者打印出来的