如何使用MediatR获得相同请求模型的不同响应类型?



我想了解MediatR是如何工作的。我从来没用过这个图书馆。下面的代码不是实际的生产代码。仅供理解之用。

假设我有两个requesthandler。每个处理程序接受ProductModel作为请求,但返回不同类型的响应。

public class GetOrdersHandler : IRequestHandler<ProductModel, IEnumerable<Order>>
{
private readonly FakeDataStore _fakeDataStore;
public GetOrdersHandler(FakeDataStore fakeDataStore)
{
_fakeDataStore = fakeDataStore;
}
public async Task<IEnumerable<Order>> Handle(ProductModel request,CancellationToken cancellationToken
{ 
return await _fakeDataStore.GetAllOrdersForProduct(request);
}
}

public class SaveProductHandler : IRequestHandler<ProductModel, Product>
{
private readonly FakeDataStore _fakeDataStore;
public SaveProductHandler(FakeDataStore fakeDataStore)
{
_fakeDataStore = fakeDataStore;
}

public async Task<Product> Handle(ProductModel request,CancellationToken cancellationToken)
{ 
return await _fakeDataStore.SaveProduct(request);
}
}

那么在同一个控制器中,我有两个动作方法

public class ProductsController : ControllerBase
{
private readonly IMediator _mediator;
public ProductsController(IMediator mediator) => _mediator = mediator;
[HttpPost]
public async Task<ActionResult> GetAllOrders(ProductModel model)
{ 
var product = await _mediator.Send(model);
return Ok(product);
}

[HttpPost]
public async Task<ActionResult> SaveProduct(ProductModel model)
{ 
var product = await _mediator.Send(model);
return Ok(product);
}
}

基于MediatR代码,这可能不起作用。看起来Send方法基于请求类型创建处理程序的实例。它保留了RequestType的字典和相应的处理程序。

如果我的假设是正确的,那么这是否意味着我将不得不为每个将使用Send方法的操作方法创建唯一的请求模型?

这是否意味着我将不得不为每个将使用Send方法的操作方法创建唯一的请求模型?

是的。

我们通常为每个请求创建一个类,也为每个响应创建一个类。

例如:

public class GetOrdersRequest : IRequest<GetOrdersResponse>
{
public Guid ProductId { get; set; }
}
public class GetOrdersResponse
{
public IEnumerable<Order> Orders { get; set; }
}

处理程序接收请求并返回响应。

public class GetOrdersHandler : IRequestHandler<GetOrdersRequest, GetOrdersResponse>
{
private readonly IOrdersRepository _ordersRepository;
public GetOrdersHandler(IOrdersRepository ordersRepository)
{
_ordersRepository = ordersRepository;
}
public async Task<GetOrdersResponse> Handle(GetOrdersRequest request, CancellationToken cancellationToken)
{
return new GetOrdersResponse
{
Orders = await _ordersRepository.GetOrdersThatContainProduct(request.ProductId)
}
}
}

最新更新