确定信号R连接状态,而不广播Clients.All.someMethod()并炸毁客户端资源

use*_*050 5 javascript asp.net-mvc signalr signalr-hub signalr.client

我担心Clients.All在我的C#Signal R集线器类中使用

Clients.All.setConnectionStatus(profileId, true);
Run Code Online (Sandbox Code Playgroud)

我在两者中调用它OnConnected()OnDisconnected(bool stopCalled) 显示我登录用户的在线状态. OnDisconnected()并不是那么糟糕,因为只有在有人实际注销时才会被调用

恩.

public override Task OnConnected()
{
   string profileId = Context.User.Identity.Name;
   _connections.Add(profileId, Context.ConnectionId);
    Clients.All.setConnectionStatus(profileId, true);
    return base.OnConnected();
 }

public override Task OnDisconnected(bool stopCalled)
{
    string profileId = Context.User.Identity.Name;
    _connections.Remove(profileId, Context.ConnectionId);
    if (stopCalled == false) // log off only
        Clients.All.setConnectionStatus(profileId, false);
     return base.OnDisconnected(stopCalled);
}
Run Code Online (Sandbox Code Playgroud)

我担心 - >用浏览器中不断运行的javascript代码炸毁用户机器客户端!

场景 - >如果我有~~ 1000个在线用户并登录到不同的页面,我将向他们所有人发送信号R连接 Clients.All.setConnectionStatus(profileId, true);

在javascript集线器中看起来像下面这可能很容易最终炸毁用户浏览器,因为它将不断接收这些广播连接状态调用!

scope.chat = $.connection.chatHub;

// Receive and set the connection status
scope.chat.client.setConnectionStatus = function(profileId, isConnected) {
  // look for prfileId in html
  var $profileStatusElement = $(".online-status-profile[data-id='" + profileId + "']");
  var $profileChatElement = $(".online-status-chat[data-id='" + profileId + "']");
  
  if (isConnected === true) {
    // change the online status
  } else {
    // change the online status
  }
};
Run Code Online (Sandbox Code Playgroud)

我有一个聊天窗口给用户(在线),如下图所示,显示他们名字旁边的用户状态.所以我知道我发送消息的人是否在线!

当我第一次加载聊天框时,我会获取在线状态服务器端,但之后由我的集线器中的OnConnected()OnDisconnected()方法设置我正在聊天的人的在线状态.

在此输入图像描述

必须有一个更好的方法然后向我网站上的"所有"在线用户广播信号?但我能想到的唯一方法是在一些javascript计时器上经常轮询状态,但我讨厌这个想法!

另一种方法是保留每个人正在聊天的内存集合,但这似乎可能会变得非常混乱,并且最终可能不会非常准确,因为可能会有很多东西介于两者之间客户端和服务器可能会导致中断错误管理谁与谁连接的内存集合!任何想法或想法将非常感谢!!

仅供参考 - >我还有一个消息页面,其中显示了我与用户最近所有会话的列表,如下所示.在此页面上,我还显示了这些用户的在线状态.在这个页面上我获取服务器上的每个用户的在线状态我渲染页面,一样的聊天框前,但一旦加载页面时,它到OnConnected()OnDisconnected(bool stopCalled)设置页面上的每个用户的在线状态.

在此输入图像描述

Ami*_*rzi 3

您正在以正确的方式使用 signalR 。我根据您的担忧/情况为您提供指导:

我担心 -> 用浏览器中不断运行的 JavaScript 代码炸毁用户机器客户端!

不要忘记您正在使用浏览器底层功能(WebSocket),因此我们别无选择,除非在客户端加载的页面中运行一些js代码。您可以在此处利用浏览器功能。

场景 -> 如果我有 > ~1000 个用户在线并登录并遍历不同的页面,我将向他们所有人广播信号 R 连接Clients.All.setConnectionStatus(profileId, true);

在提出任何解决方案之前,我建议您在应用程序中使用分组逻辑。分组减少了同步量

如果您在公共聊天室(可能包含大量人员)工作,那么通过采用服务器端策略,您将使您的代码变得肮脏!是的,任何导航或刷新页面的用户都可能导致所有客户端的冗余更新。最佳解决方案是 将页面转换为 SPA(使用 API 调用或 Ajax 调用),无需刷新页面。我相信任何实时 Web 应用程序都应该利用现代 Web 技术。这将解决您遇到的几乎所有问题(例如,没有页面刷新、没有重新运行、没有断开等...)。

像使用 js 计时器来获取用户最新状态这样的解决方案并不干净或不可取。