Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/303.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 在Asp.Net核心Web API中使用MassTransit消息时,如何对用户进行身份验证?_C#_Authentication_Asp.net Core Webapi_Masstransit - Fatal编程技术网

C# 在Asp.Net核心Web API中使用MassTransit消息时,如何对用户进行身份验证?

C# 在Asp.Net核心Web API中使用MassTransit消息时,如何对用户进行身份验证?,c#,authentication,asp.net-core-webapi,masstransit,C#,Authentication,Asp.net Core Webapi,Masstransit,我有几个Asp.Net核心Web API,它们使用承载身份验证和IdentityServer 4.AccessTokenValidation中间件来检查令牌、验证用户和创建声明。这适用于HTTP请求 我正在将这些API配置为使用RabbitMQ作为传输的MassTransit端点(用于发布和消费消息)。我按照说明将MassTransit添加到API和设置消息使用者。典型的工作流程如下所示: HTTP请求API>在MassTransit上发布消息>RabbitMQ>在另一个API中使用的消息 我很

我有几个Asp.Net核心Web API,它们使用承载身份验证和
IdentityServer 4.AccessTokenValidation
中间件来检查令牌、验证用户和创建声明。这适用于HTTP请求

我正在将这些API配置为使用RabbitMQ作为传输的MassTransit端点(用于发布和消费消息)。我按照说明将MassTransit添加到API和设置消息使用者。典型的工作流程如下所示:

HTTP请求API>在MassTransit上发布消息>RabbitMQ>在另一个API中使用的消息

我很难理解的是,在总线外消费消息时,如何创建
ClaimsPrincipal
,以便知道代表哪个用户执行操作?如果不是HTTP请求,则不会调用AuthenticationHandler

到目前为止我所尝试的:

我想我应该通过在消息头中传递一个令牌(和/或单个声明值)来实现这一点。当使用
masstTransit.PublishContextExecuteExtensions.publish
发布消息时,发布部分似乎很容易成为MassTransit。这使我能够将带有识别用户信息的信息发送到传输上,并且可以通过手动查看标题在消费者中查看这些信息,例如:

public class SomeEventConsumer : IConsumer<SomeEventData>
{
    public async Task Consume(ConsumeContext<SomeEventData> context)
    {
        var token = context.Headers["token"];
    }
} 
。。。然后将其添加到管道中

IBusControl CreateBus(IServiceProvider serviceProvider)
{
    return Bus.Factory.CreateUsingRabbitMq(cfg =>
    {
        cfg.Host("rabbitmq://localhost");
        cfg.UseAuthenticationFilter();
        // etc ...
    });
}

这就是我被困的地方。我不知道如何验证用户的请求范围。如果不是HTTP请求,我不确定这里的最佳实践是什么。如有任何建议或建议,我们将不胜感激。谢谢…

用户身份验证是web关注的问题。应该使用您的身份提供者正确地完成此操作。您发送到总线的消息可以包含标识本身、作用域和sub,无论您在声明中得到什么。用户必须已经过身份验证。@AlexeyZimarev,所以我只需要在生产者端序列化主体声明并将其添加到消息头。在消费者端,我只需要读取它们,反序列化到ClaimsPrincipal并设置当前线程。这样可以吗?@Gavin Sutherland您为什么决定在用户声明的情况下传递令牌?@АСаааССаа。。因为我可以通过查询创建令牌的可信机构服务(内省端点)来验证令牌是否有效。通过这样做,我可以确信代币中的声明是真实的,而不是恶意的。例如,如果我刚刚传递了用户声明,如何确保来自
admin@some.system
真的是来自那个人吗?@GavinSutherland您的应用程序在发送消息之前已经对用户进行了身份验证,是吗?消费者是否可以假定消息是由受信任的服务发送的?这也避免了令牌过期的问题(如果令牌在HTTP请求期间有效,但在使用者可以处理消息之前过期怎么办?)
IBusControl CreateBus(IServiceProvider serviceProvider)
{
    return Bus.Factory.CreateUsingRabbitMq(cfg =>
    {
        cfg.Host("rabbitmq://localhost");
        cfg.UseAuthenticationFilter();
        // etc ...
    });
}