我想问一个简单的问题,似乎是我无法找到答案的问题。这里是jist,我想使用除Context.ConnectionId之外的唯一值来识别用户
所以,在我的hub类中我有这个方法来生成一个唯一的guid,当我通过我的javascript启动连接时调用这个方法
// My hub class
//...
public void GenerateGuid()
{
var guid = Guid.NewGuid().ToString();
Clients.Caller.myGuid(guid);
}
// My javascript
$.connection.hub.start().done(function(){
$.connection.chatHub.server.generateGuid();
});
$.connection.chatHub.client.myGuid = function (guid){
if (docCookies.getItem("guid") === null){
docCookies.setItem("guid", guid);
}
}
我还设置了IUserIdProvider的自定义实现者(正如这些文档https://www.asp.net/signalr/overview/guide-to-the-api/mapping-users-to-connections#IUserIdProvider中所建议的那样)使用IPrincipal.Identity.Name以外的其他内容(因为我的用户不是#39; t认证))
我认为这需要一点修改,因为我不确定在没有定义guid的情况下返回什么
public class MyUserIdProvider : IUserIdProvider
{
public string GetUserId(IRequest request)
{
try
{
if (request.Cookies["guid"] != null)
{
return request.Cookies["guid"].Value;
}
}
catch (KeyNotFoundException kex)
{
// what to return here?
return Guid.NewGuid().ToString();
}
// what to return here?
return "";
}
}
。 (这是在我的Startup.cs中设置的,所以不用担心)
GlobalHost.DependencyResolver.Register(typeof(IUserIdProvider), () => new MyUserIdProvider());
所以,所有这些我认为有两个问题
MyUserIdProvider
课程?Context.ConnectionId
:return Groups.Add(Context.ConnectionId, [room]);
答案 0 :(得分:0)
IUserIdProvider.GetUserId
之前,在建立连接时调用 GenerateGuid
。因此,cookies
在该阶段没有用处。您必须根据request
设置自己的存储空间,例如:
public class MyUserIdProvider : IUserIdProvider
{
private static IDictionary<string, Guid> _tokens;
static MyUserIdProvider()
{
_tokens = new ConcurrentDictionary<string, Guid>();
}
private static string Key(IRequest request)
{
var key = request.QueryString["connectionToken"];
return key;
}
public static string UserId(IRequest request)
{
return _tokens[Key(request)].ToString();
}
public string GetUserId(IRequest request)
{
var key = Key(request);
_tokens[key] = Guid.NewGuid();
return _tokens[key].ToString();
}
}
使用该存储,您可以在hub方法中从request
检索您的用户ID:
public void GenerateGuid()
{
var guid = MyUserIdProvider.UserId(Context.Request);
Clients.Caller.myGuid(guid);
}