使用 SignalR 通过客户端的 Windows 用户名向特定客户端发送数据
Send data to a specific client by the client's Windows User Name with SignalR
我有一种类似于桌面的 Web 应用程序,带有可拖动的项目,并且在拖放每个项目时,数据库都会使用新的序列化数据进行更新。现在每当一个用户改变他的布局时,他所有登录的计算机都应该实时更新。
我将如何使用此 属性:
将数据仅发送给用户
User.Identity.Name
基本上它应该是这样的:
this.Clients.WithWindowsName("windowsusername").sendData(data);
首先,您需要将windows 名称发送到服务器。最快的方法是将其作为 header 从客户端发送,因为它将包含在 Start()
调用中,因此您不需要额外的 proxy.Invoke()
:
客户端
_connection = new HubConnection(_uri);
_connection.Headers.Add("windowsName", "John");
await _connection.Start();
服务器端
那"windowsName" header 将是你的身份。为确保 SignalR 将 header 识别为身份,您需要创建 IUserIdProvider
:
的实现
using Microsoft.AspNet.SignalR;
namespace YourServer
{
public class UserIdProvider : IUserIdProvider
{
public string GetUserId(IRequest request)
{
return request.Headers.Get("windowsName");
}
}
}
然后将其插入全局依赖解析器:
public class Startup
{
public void Configuration(IAppBuilder app)
{
var idProvider = new UserIdProvider();
GlobalHost.DependencyResolver.Register(typeof(IUserIdProvider), () => idProvider);
// TODO configure signalR here
}
}
无论何时访问 User.Identity.Name
,它都会匹配 "windowsName",但您甚至不需要它,如下所述。
如您所说,一个用户可以从多台计算机登录。处理此问题的最佳方法是创建 SignalR 组:
public override Task OnConnected()
{
var windowsName = Context.Headers.Get("windowsName");
Groups.Add(Context.ConnectionId, windowsName);
return base.OnConnected();
}
这将使用 Windows 机器的名称创建一个 SignalR 组。
如果用户 logs-in 使用其他机器,他将被添加到同一组。
您不需要删除 OnDisconnected
中的任何内容,因为 SignalR 会为您处理。
群组非常方便,因为每当您向群组发送消息时,所有连接的机器都会收到通知:
Clients.Group("John").sendData(data);
Clients.Group(User.Identity.Name).sendData(data);
因此,即使是单个用户(从多台计算机连接)也可以创建一个组。
我有一种类似于桌面的 Web 应用程序,带有可拖动的项目,并且在拖放每个项目时,数据库都会使用新的序列化数据进行更新。现在每当一个用户改变他的布局时,他所有登录的计算机都应该实时更新。
我将如何使用此 属性:
将数据仅发送给用户User.Identity.Name
基本上它应该是这样的:
this.Clients.WithWindowsName("windowsusername").sendData(data);
首先,您需要将windows 名称发送到服务器。最快的方法是将其作为 header 从客户端发送,因为它将包含在 Start()
调用中,因此您不需要额外的 proxy.Invoke()
:
客户端
_connection = new HubConnection(_uri);
_connection.Headers.Add("windowsName", "John");
await _connection.Start();
服务器端
那"windowsName" header 将是你的身份。为确保 SignalR 将 header 识别为身份,您需要创建 IUserIdProvider
:
using Microsoft.AspNet.SignalR;
namespace YourServer
{
public class UserIdProvider : IUserIdProvider
{
public string GetUserId(IRequest request)
{
return request.Headers.Get("windowsName");
}
}
}
然后将其插入全局依赖解析器:
public class Startup
{
public void Configuration(IAppBuilder app)
{
var idProvider = new UserIdProvider();
GlobalHost.DependencyResolver.Register(typeof(IUserIdProvider), () => idProvider);
// TODO configure signalR here
}
}
无论何时访问 User.Identity.Name
,它都会匹配 "windowsName",但您甚至不需要它,如下所述。
如您所说,一个用户可以从多台计算机登录。处理此问题的最佳方法是创建 SignalR 组:
public override Task OnConnected()
{
var windowsName = Context.Headers.Get("windowsName");
Groups.Add(Context.ConnectionId, windowsName);
return base.OnConnected();
}
这将使用 Windows 机器的名称创建一个 SignalR 组。
如果用户 logs-in 使用其他机器,他将被添加到同一组。
您不需要删除 OnDisconnected
中的任何内容,因为 SignalR 会为您处理。
群组非常方便,因为每当您向群组发送消息时,所有连接的机器都会收到通知:
Clients.Group("John").sendData(data);
Clients.Group(User.Identity.Name).sendData(data);
因此,即使是单个用户(从多台计算机连接)也可以创建一个组。