如何在ASP.NET Core中注册和使用MediatR管道处理程序?

14
1个回答

27

你提到的帖子使用的是MediatR 2.x版本。
不久前发布了MediatR 3.0,内置了对管道的支持。建议您阅读相关文档

简而言之,MediatR现在公开了一个IPipelineBehavior<TRequest, TResponse>,您在容器中注册的实例将被MediatR自动发现并构建处理程序。

以下是在ASP.NET Core中可能看起来像什么:

public class MyRequest : IRequest<string>
{
}

public class MyRequestHandler : IRequestHandler<MyRequest, string>
{
    public string Handle(MyRequest message)
    {
        return "Hello!";
    }
}

public class TracingBehavior<TRequest, TResponse> : IPipelineBehavior<TRequest, TResponse>
{
    public async Task<TResponse> Handle(TRequest request, RequestHandlerDelegate<TResponse> next)
    {
        Trace.WriteLine("Before");
        var response = await next();
        Trace.WriteLine("After");

        return response;
    }
}

非常简单,一个请求,一个处理程序和一个执行某些“日志记录”操作的行为。

注册也非常容易:

var services = new ServiceCollection();
services.AddMediatR(typeof(Program));
services.AddTransient(typeof(IPipelineBehavior<,>), typeof(TracingBehaviour<,>));
var provider = services.BuildServiceProvider();

var mediator = provider.GetRequiredService<IMediator>();

var response = await mediator.Send(new MyRequest());

只需要将开放式泛型 TracingBehavior 注册为 IPipelineBehavior 的通用实现即可。


我很好奇处理程序是如何与管道相关联的,因为我刚刚尝试了一下,它自动地就起作用了! - grokky
2
MediatR 在内部完成此操作。它通过容器解析请求处理程序,然后解析所有 IPipelineBehavior 实例并创建一个管道,其中所有行为都被链接在一起,链中的最后一个元素是实际的处理程序。如果您有兴趣阅读代码,这一切都发生在 RequestHandlerImpl<TRequest, TResponse> 类中。 - Mickaël Derriey
3
我刚意识到上述管道将被应用于所有请求。这是应该的吗?我不能有多个管道吗?例如,我可以为验证设置一个管道,仅处理特定请求,而不是所有请求吗? - grokky
9
我理解了:services.AddTransient(typeof(IPipelineBehavior<MyRequest, string>), typeof(TracingBehaviour<MyRequest, string>)); 的意思是将 TracingBehaviour<MyRequest, string> 注册为 IPipelineBehavior<MyRequest, string> 的一个瞬态服务。 - grokky

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接