How to obtain connection ID of signalR client on the server side?

前端 未结 3 1264

I need to get the connection ID of a client. I know you can get it from the client side using $.connection.hub.id. What I need is to get in while in a web servi

3条回答
  •  被撕碎了的回忆
    2020-12-12 17:07

    Taylor's answer works, however, it doesn't take into consideration a situation where a user has multiple web browser tabs opened and therefore has multiple different connection IDs.

    To fix that, I created a Concurrent Dictionary where the dictionary key is a user name and the value for each key is a List of current connections for that given user.

    public static ConcurrentDictionary> ConnectedUsers = new ConcurrentDictionary>();
    

    On Connected - Adding a connection to the global cache dictionary:

    public override Task OnConnected()
    {
        Trace.TraceInformation("MapHub started. ID: {0}", Context.ConnectionId);
        
        var userName = "testUserName1"; // or get it from Context.User.Identity.Name;
    
        // Try to get a List of existing user connections from the cache
        List existingUserConnectionIds;
        ConnectedUsers.TryGetValue(userName, out existingUserConnectionIds);
    
        // happens on the very first connection from the user
        if(existingUserConnectionIds == null)
        {
            existingUserConnectionIds = new List();
        }
    
        // First add to a List of existing user connections (i.e. multiple web browser tabs)
        existingUserConnectionIds.Add(Context.ConnectionId);
    
        
        // Add to the global dictionary of connected users
        ConnectedUsers.TryAdd(userName, existingUserConnectionIds);
    
        return base.OnConnected();
    }
    

    On disconnecting (closing the tab) - Removing a connection from the global cache dictionary:

    public override Task OnDisconnected(bool stopCalled)
    {
        var userName = Context.User.Identity.Name;
    
        List existingUserConnectionIds;
        ConnectedUsers.TryGetValue(userName, out existingUserConnectionIds);
    
        // remove the connection id from the List 
        existingUserConnectionIds.Remove(Context.ConnectionId);
    
        // If there are no connection ids in the List, delete the user from the global cache (ConnectedUsers).
        if(existingUserConnectionIds.Count == 0)
        {
            // if there are no connections for the user,
            // just delete the userName key from the ConnectedUsers concurent dictionary
            List garbage; // to be collected by the Garbage Collector
            ConnectedUsers.TryRemove(userName, out garbage);
        }
    
        return base.OnDisconnected(stopCalled);
    }
    

提交回复
热议问题