Jens Elstner
Jens Elstner

Reputation: 128

SignalR on mono Group.Add not working in OnConnected

I have a problem with SignalR running in MVC3 on mono.

I created the following Hub:

    public class TestHub : Hub
    {
      public override Task OnConnected()
      {
        Trace.WriteLine(String.Format("Join Group: {0}", Context.User.Identity.Name), "SignalR.General");
        Task addTask = Groups.Add(Context.ConnectionId, Context.User.Identity.Name);
        return addTask;
      }

      public void JoinGroup(String group)
      {
        Trace.WriteLine(String.Format("Join Group2: {0}", Context.User.Identity.Name), "SignalR.General");
        Groups.Add(Context.ConnectionId, group);
      }

      public void Echo(String group, String value)
      {
        Trace.WriteLine(String.Format("Echo: {0}, {1}", group, value), "SignalR.General");
        Clients.Group(group).echo(value);
      }
    }

The main problem is the following:

A user is signed in via Forms auth and their name is correctly found in Context.User.Identity.Name. When the client connects, OnConnected is called and the connection is added to a single user group with the same name as the username. When I call the Echo function from the client with the group name being the username then I get the correct response (response is sent to client) IF I am hosting in IIS but I get no response when hosting in mono.

If on the other hand I call JoinGroup from the client first, it works in IIS and Apache on mono. Sending a message to Clients.All works in IIS and mono as well but I need the message to arrive only for a specific user.

I tried different variations of this code but have no idea why the group registration should not work in OnConnected.

Any ideas would be greatly appreciated since I wasted 2 days on this problem already.

Upvotes: 1

Views: 665

Answers (1)

Jens Elstner
Jens Elstner

Reputation: 128

I dug a bit deeper into the problem and came up with this root cause:

When the client connects, it tries to connect first using Server Sent Events. This connection seems to work and is received by the server, firing OnConnected and correctly returning the group id to the client. For some reason though, when running on apache2 and mono this response is never received and the "open" event of the EventSource object also does not fire. This means that after 3 seconds SignalR times out this connection request on the client and assumes that SSE is not working and starts a longPolling session.

This session connects successfully and can send and receive data but the connection id has been sent to the server already and OnConnected is not fired again so there is no way for my hub to get the second connection attempt and the client will not get the group id.

Starting the client directly with longPolling through $.connection.hub.start({ transport: "longPolling" }) fixes the problem at the expense of using longPolling only.

Upvotes: 3

Related Questions