C# 如何访问用户';s在将SignalR Hub与ASP.NET MVC 5项目一起使用时在标识2中声明?

C# 如何访问用户';s在将SignalR Hub与ASP.NET MVC 5项目一起使用时在标识2中声明?,c#,asp.net,asp.net-mvc,asp.net-mvc-5,signalr,C#,Asp.net,Asp.net Mvc,Asp.net Mvc 5,Signalr,我有一个应用程序,它是在Asp.NETMVC5框架之上使用c#编写的 我正在使用创建浏览器和服务器之间的WebSocket通信,以将消息从服务器推送到浏览器 但是,我需要能够访问登录用户的ClaimsIdentity对象,以便确定要播客的消息 通常,我会像这样访问身份声明 IPrincipal user = System.Web.HttpContext.Current.User IIdentity identity = user.Identity; var claims = (IEnumerab

我有一个应用程序,它是在Asp.NETMVC5框架之上使用c#编写的

我正在使用创建浏览器和服务器之间的WebSocket通信,以将消息从服务器推送到浏览器

但是,我需要能够访问登录用户的
ClaimsIdentity
对象,以便确定要播客的消息

通常,我会像这样访问身份声明

IPrincipal user = System.Web.HttpContext.Current.User
IIdentity identity = user.Identity;
var claims = (IEnumerable<Claim>)identity.Claims;
如何在我的中心正确访问用户声明

在我使用Framework 4.5.1时,我在我的Web.config中将以下键添加到我的
appSettings

<add key="aspnet:UseTaskFriendlySynchronizationContext" value="true"/>

如果使用信号集线器并希望授权同一集线器下的方法,则必须使用集线器上的authorize属性。i、 e

[Authorize]
public class MessagingHub: Hub
{
    public Task Send(string data)
    {
        return Clients.Caller.SendAsync("Send", "Data To Send");
    }
}
为了在Hub方法中访问声明或用户身份,例如上面的Send,则应具有以下内容:

[Authorize]
public class MessagingHub: Hub
{
   public Task Send(string data)
  {
     var identity = (ClaimsIdentity)Context.User.Identity;
     //one can access all member functions or properties of identity e.g, Claims, Name, IsAuthenticated... 
      return Clients.Caller.SendAsync("Send", "Data To Send");
  }
}
如果像我这样使用Json Web令牌(JWT)或仅使用令牌身份验证,那么从客户端就可以使用它来调用集线器的Send方法

NB:就我而言,客户端是一个有角度的6应用程序。

import { HubConnection } from "@aspnet/signalr";
import * as signalR from '@aspnet/signalr';
...
private _messagingHubConnection: HubConnection | undefined;
public async: any;
...
constructor(){}
...
 SendMessg(): void {
    if (this._messagingHubConnection) {
      this._messagingHubConnection.invoke('Send');
    }
  }
...

ngOnInit(){
    this._messagingHubConnection= new signalR.HubConnectionBuilder()
      .withUrl("messaging", { accessTokenFactory: () => "jwt_token" }) //have a logic that gets the current user's authentication token from the browser 
      .build();

    this._messagingHubConnection.start().then(() => {
        this.SendMessg();
      }).catch(err => console.error(err.toString()));

    if (this._messagingHubConnection) {
      this._messagingHubConnection.on('Send', (data: any) => {
        //data represents response/message received from Hub method'd return value.
      });

    }
}
NB:我正在使用.Net Core 2.1,因此请务必注册集线器。 此外,假设信号机已经设置好

对于.Net Core,请确保在StartUp.cs中:

services.AddSignalR(); // under ConfigureServices

app.UseWebSockets();
app.UseAuthentication();
app.usesigner(路由=>{
routes.MapHub(“/messaging”);
});
NB:从一开始,我意识到上面的顺序很重要,以防有人出现任何问题。i、 e.据我所知,上述顺序是正确的。

import { HubConnection } from "@aspnet/signalr";
import * as signalR from '@aspnet/signalr';
...
private _messagingHubConnection: HubConnection | undefined;
public async: any;
...
constructor(){}
...
 SendMessg(): void {
    if (this._messagingHubConnection) {
      this._messagingHubConnection.invoke('Send');
    }
  }
...

ngOnInit(){
    this._messagingHubConnection= new signalR.HubConnectionBuilder()
      .withUrl("messaging", { accessTokenFactory: () => "jwt_token" }) //have a logic that gets the current user's authentication token from the browser 
      .build();

    this._messagingHubConnection.start().then(() => {
        this.SendMessg();
      }).catch(err => console.error(err.toString()));

    if (this._messagingHubConnection) {
      this._messagingHubConnection.on('Send', (data: any) => {
        //data represents response/message received from Hub method'd return value.
      });

    }
}

从技术上讲,我已经回答了上面的问题,但是是从.NET核心&Angular上下文;我想大多数(如果不是所有的话)实现都遵循相同的方法。

大家都会遗漏一件重要的事情

与控制器不同,您将无法访问Hub中构造函数中的声明。连接后访问声明。如下图所示

 [Authorize]
    public class YourHub: Microsoft.AspNetCore.SignalR.Hub
    {

          public override async Task OnConnectedAsync()
          {
             ...
             var identity = (ClaimsIdentity)Context.User.Identity;
          }
  }

你在用信号集线器吗?有属性,您检查了吗?@Zabavsky
上下文
对象本身id为空。您试图从何处访问上下文?从构造函数。我的构造函数称为base()类。这里有相关文档:。是否正确注释了中心方法?未回答问题。问题是关于Asp.NETMVC5而不是ASPNETCore。
 [Authorize]
    public class YourHub: Microsoft.AspNetCore.SignalR.Hub
    {

          public override async Task OnConnectedAsync()
          {
             ...
             var identity = (ClaimsIdentity)Context.User.Identity;
          }
  }