我的问题是,如果我在两个不同的选项卡上打开相同的页面(在Chrome中),第一页加载完毕,但是第二页不调用服务器的功能 – 只有在关闭第一页的时候。
所以据我所知,他们可能是与浏览器相关的连接限制,不允许SignalR连接多一次(实际上是两个,一个用于接收,一个用于发送)
更新:我已经找到我们的其他标签开放,但现在我检查了它,它只允许4个选项卡/页面与连接活动。如果我尝试将相同的页面放在一个新的标签上,没有数据被发送,当我关闭其他选项卡之一时,新的选项卡立即发送数据。
如果有任何解决方案,我想知道的是什么,因为如果用户决定在两个选项卡上打开相同的页面,我希望这种连接可用。
我不相信它与IIS有任何关系,因为我知道它可以接受数千个连接。
解决方法
存储事件允许您在标签之间传播数据,同时保持单个SignalR连接打开(从而防止连接饱和)。调用localStorage.setItem(‘sharedKey’,sharedData)会引发所有其他选项卡(而不是调用者)中的存储事件:
$(window).bind('storage',function (e) { var sharedData = localStorage.getItem('sharedKey'); if (sharedData !== null) console.log( 'A tab called localStorage.setItem("sharedData",'+sharedData+')' ); });
您可以测试($ .connection.hub.state === 1)以确定给定的选项卡是否应通过localStorage(由Alex提供)通知其他选项卡,以防止重复的localStorage.setItem调用。
Facebook通过在多个子域中提供持久连接来克服这种浏览器限制,但这会使部署和测试复杂化。
注意事项
旧连接:在Alex的解决方案中,您需要小心Disconnect()不被调用(例如异常),并且使用旧的集线器连接填充HubConnections存储桶(或存储库)。如果会话ID不改变(可能发生),这可能会阻止新客户端建立SignalR连接,即使没有活动。或者,时间戳新连接并具有滑动过期,以最小化潜在的影响。
锁定:localStorage可能会受到竞争条件的限制,因为它不执行任何锁定为described here。
要支持不同类型的事件,您应该对JSON消息中的eventType进行编码,并在存储事件上进行测试。
回退
如果无法建立SignalR连接,则每45秒钟我将轮回服务器以检索通知计数。
如果你不想使用localStorage,你可以使用cookies,但它不是那么干净。