Connection ID when calling SignalR Core Hub method

2019-03-05 15:23发布

问题:

This is a follow-up to another question and answer. What's the effect of calling HubContext.Clients.Caller or HubContext.Clients.Others from the controller? I see it depends on the connection ID. What value would it have in this situation?

If the connection ID (and thus Caller and Others) is invalid then (from within the controller action) how could I obtain a connection ID (for the client currently calling the Web API) that I could use with HubContext.Clients's methods?

回答1:

What's the effect of calling HubContext.Clients.Caller or HubContext.Clients.Others from the controller? I see it depends on the connection ID. What value would it have in this situation?

There is neither .Caller nor .Others on HubContext.Clients (of type HubClients<THub>).

"It's not possible to access those from IHubContext. Caller and Others both depend on knowing which client is the caller. When you're in IHubContext, we don't know and there may not even be a current caller since you could be in an MVC controller action, etc."
— aspnet/SignalR#2274 (comment)

(from within the controller action) how could I obtain a connection ID (for the client currently calling the Web API) that I could use with HubContext.Clients's methods?

"there is no way of knowing who the current caller is from the IHubContext"
— aspnet/SignalR#2274 (comment)

Using Groups and Users is one way to mitigate this.

"If you have access to the User ID of the user who initiated the action, you can use .Users(userId) to send a message to all of that user's connections. Similarly, you add the SignalR connections to a group and send to that group using .Group(groupName)"
— aspnet/SignalR#2274 (comment)

Alternatively, get the connection ID on the client side.

You can get the connection ID on the client that calls the API, and then send it to the controller.

Hub:

public string GetConnectionId()
{
    return Context.ConnectionId;
}

Client:

hub.invoke('getConnectionId')
    .then(function (connectionId) {
        // Send the connectionId to controller
    });