SignalR client callback method getting called multiple times
Asked Answered
N

3

9

We have a SignalR client call back method, which gets called as many times as we move away from and come back to it's containing page. For example: page is salesUpdate.html (Angular template), on this page when coming for the first time, the call back would execute once upon it's event. Now when we move away from this page to another page (say purchaseUpdate.html), and come back to this page i.e. salesUpdate.html, this SignalR client call back method would execute twice. It will execute as many times as we move away from the page and come back to it. From server, this method is called from ASP.NET Web API, and Web API is hit only one time, all subsequent execution of call back does not hit Web API. Here is the client call back method:

var con;
var apiMsgProxy;
$(document).ready(function () {
        con = $.hubConnection('http://localhost:51123/signalr');
        apiMsgProxy = con.createHubProxy('salesHub');

        apiMsgProxy.on('SendSaleUpdate', function (uMsg) {
            console.log("Call back SendSaleUpdate called - " + uMsg);
        });
        con.start().done(function () {
        console.log("SignalR connection opened - " + con.state);
        }).fail(function () { 
            console.log('Could not Connect SignalR hub!'); 
        });
});

Any pointer towards this will be greatly appreciated.

Namedropper answered 11/9, 2015 at 14:30 Comment(3)
Where in your angular app is the hub connection being instantiated? Is it in a controller or a service or something?Castellanos
This is in jQuery $(document).ready() on the HTML page's script block where it opens hub connection and creates hub proxy. This is not in Angular app controller/service.Namedropper
Can you confirm, that you're hitting the Reconnected (n-1 times) event? Inspect the ConnectionId maybe.Cranwell
T
11

I know that this question was asked a long time ago. But I had the same issue and found a solution. Thought I'd share it with everyone. In the question, the "salesHub" gets inited and event handler is being added using the hub's .on("SendSaleUpdate") method on page load. Apparently, if you don't "turn off" that handler it'll be invoked by SignalR as mane times as the client inited the hub (visited the same page while the same connection is still opened.) To prevent this from happening, you need to call hub's .off("SendSaleUpdate") method when the user leaves the page. That solved the same issue for me.

Tetragram answered 8/5, 2016 at 17:8 Comment(5)
I've the same issue and couldn't find any solution. I use signalr on my xamarin.forms project and we have no .off method. Do you know anything about itEvan
I am stuck with a similar issue. My doubt is , if I "turn off", will it stop receiving updates from the server?Stanley
I am having the same issue with Xamarin forms. How did you solve @EvanCroup
Wonderful answer, i've been struggling with this around 2 months.Byrn
Perfect solution. Thank you very much.Cotton
F
2

Please don't use the default auto-generated proxy :

var contosoChatHubProxy = $.connection.contosoChatHub;
contosoChatHubProxy.client.addContosoChatMessageToPage = function (name, message) {
    console.log(name + ' ' + message);
};

Instead, instantiate a new connection, and define your client methods without using generated proxy :

var connection = $.hubConnection(`${yourApplicationPath}/signalr`, { useDefaultPath: false });
var contosoChatHubProxy = connection.createHubProxy('contosoChatHub');
contosoChatHubProxy.off('addContosoChatMessageToPage').on('addContosoChatMessageToPage', function(name, message) {
    console.log(name + ' ' + message);
});

I discovered this bug in SignalR version 2.2.2 up to 2.4.3, with auto generated proxy, it will call your client event handler contosoChatHubProxy.client.addContosoChatMessageToPage as many times as you do $.connection.contosoChatHub.hub.start().

I think that inside start(), it will reuse the current proxy, and by mistake, it double the event handler attached to the client's event : contosoChatHubProxy.client.addContosoChatMessageToPage.

I solved this issue finally by instantiating a proxy and not using the auto-generated one.

Regards

Funiculate answered 3/3, 2022 at 16:26 Comment(0)
C
1

it is an old question but as I found the solution in my case so updating it may help someone. So in my case, as apiMsgProxy is a global variable so each time page refreshes and reloaded it will register the SendSaleUpdate function each time and as many times as it registered it will be called that many time

Cavie answered 15/1, 2020 at 8:35 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.