5

I am using @aspnet/signalr to connect to a hub and from the hub i am calling the method to return me some data.

When i first initialize the server the connection is established normally, but if i refresh the window 3 or 4 times the client stop sending connection request to the server.

I tried logging the HubConnection, the connectionState at first is equal to 1 but after the problem accrues the connectionState is alwase equal 0

Here is how i am building the hubConnection:

buildConnection() {
this.hubConnection = new HubConnectionBuilder()
.withUrl(this.tradesService.getStockQuotationsHubUrl())
.build();
this.hubConnection.serverTimeoutInMilliseconds = 1000 * 10;
this.hubConnection.onclose(() => setTimeout(() => this.startSignalRConnection(), 2000));}

Here is how i am starting the hubConnection:

startConnection() {
    this.hubConnection
      .start()
      .then(() => {
      this.hubConnection.on('updateMethod', (data: any) => {
        
          this.store.push([
            { type: 'update', key: data.stockID, data },
          ]);
         
        });
      this.dataSource = new DataSource({
          store: this.store,
          reshapeOnPush: true,
        });
      });}

Note: I am listing to 5 hubs at once in my page but the only one having problems is this one.

[Update]

The problem is from the server because when i restart the server the connection is reestablished between the client and the server, but if the client refresh or quit the page for multiple times the hub does not even try to connect to the client

public class StockQuotationsHub : Microsoft.AspNetCore.SignalR.Hub
  {
    private string SectorID { get; set; }
    private int TradingSession { get; set; }
    private int MarketID { get; set; }

public static StockQuotationExt stockQuotationExt { get; set; }
private readonly StockQuotationTicker _stockTicker;

public StockQuotationsHub(StockQuotationTicker stockTicker){
    _stockTicker = stockTicker;
}

public override Task OnConnectedAsync(){
return base.OnConnectedAsync();
}

public IEnumerable<StockQuotation> GetAllStockQuotations(string[] stockID, string sectorID, int tradingSession, int marketType){
    return _stockTicker.
    GetAllStocks(Context.ConnectionId, stockID, sectorID, tradingSession, marketType);
        }

public override async Task OnDisconnectedAsync(Exception exception){
    await base.OnDisconnectedAsync(exception);
}

and here is my stock ticker class:

public IEnumerable<StockQuotation> GetAllStocks(string connectionId, string[] stockID, string sectorID, int tradingSession, int marketType)
    {
        _stocks = new List<StockQuotation>();
        _stocks = Task.Run(async () => await GetStockQuotationModelAsync("", 0, 1, 0)).Result.ToList();
        this.MaxTimeStamp = _stocks.Max(s => s.TStamp);
        this.SectorID = sectorID;
        this.TradingSession = tradingSession;
        this.MarketID = marketType;

        AddToGroups(connectionId, stockID);

        if (_timer==null)
            _timer = new Timer(UpdateStockPrices, null, _updateInterval, _updateInterval);

        if (stockID.Length == 0)
        {
            return _stocks;
        }
        else
        {
            var stocksList = new List<StockQuotation>();
            foreach (var stock in stockID)
            {
                stocksList.AddRange(_stocks.Where(s => s.StockID == stock).ToList());
            }
            return stocksList;
        }
    }

private void AddToGroups(string connectionId, string[] stockID)
        {
            if (_stocks.Count > 0)
            {
                if (stockID.Length == 0)
                {
                    Hub.Groups.AddToGroupAsync(connectionId, "ALL");
                }
                else
                {
                    foreach (var stock in stockID)
                    {
                        Hub.Groups.AddToGroupAsync(connectionId, stock);
                        var s = _stocks.FirstOrDefault(s => s.StockID == stock);
                        if(s != null)
                        {
                        s.Snapshots = new List<double>(GetStockQuotationSnapshots(stock));
                        }
                    }
                }
            }
        }
private void AddToGroups(string connectionId, string[] stockID)
        {
            if (_stocks.Count > 0)
            {
                if (stockID.Length == 0)
                {
                    Hub.Groups.AddToGroupAsync(connectionId, "ALL");
                }
                else
                {
                    foreach (var stock in stockID)
                    {
                        Hub.Groups.AddToGroupAsync(connectionId, stock);
                        var s = _stocks.FirstOrDefault(s => s.StockID == stock);
                        if(s != null)
                        {
                        s.Snapshots = new List<double>(GetStockQuotationSnapshots(stock));
                        }
                    }
                }
            }
        }

I really appreciated the help.

Kardon63
  • 337
  • 1
  • 5
  • 18
  • First of all, update your package from `@aspnet/signalr` to `@microsoft/signalr` since this is the new package and the old one is not supported now. – Kiril1512 Jul 17 '20 at 10:19
  • Are you destroying your connection for ngDestroy hook ? If not, you try to destroy it. – mr. pc_coder Jul 17 '20 at 10:26
  • do i call `this.hubConnection.stop()` or just do `this.hubConnection = null`? – Kardon63 Jul 17 '20 at 10:27
  • @Kiril1512 thanks for the suggestion, i did upgrade to `@microsoft/signalr` but the problem is still the same – Kardon63 Jul 17 '20 at 10:44
  • 2
    @Kardon63 yes this will not solve the problem, but at least you are using the latest version of SignalR and now you are also able to use the AutomaticReconnect feature. – Kiril1512 Jul 17 '20 at 11:00

2 Answers2

0

Eventually the problem was that the project type was MVC, so I changed it to be webApi and everything worked successfully

Kardon63
  • 337
  • 1
  • 5
  • 18
0

Even if you fix it I would like to recommend you to add the following code in order to know exactly the root cause of disconnection.

First of all enable the extended debug info in the service configuration:

services.AddSignalR(o =>
            {
                o.EnableDetailedErrors = true;
            });

Furthermore, you need to attach to the event Closed in HubConnection like that:

hubConnection.Closed += (exception) =>
            {
                if (exception == null)
                {
                    Console.WriteLine("Connection closed without error.");
                }
                else
                {
                    Console.WriteLine($"Connection closed due to an error: {exception}");
                }
                return null;
            };