是否有一种方法可以让每个用户而不是每个选项卡运行一个服务器发送事件?

Is there a way to have one server-sent-event running per user not per tab?

本文关键字:运行 选项 一个 事件 服务器 用户 方法 一种 是否      更新时间:2023-09-26

我遇到了很多问题,因为我的用户使用多个浏览器的选项卡来使用同一个应用程序。

问题是,每个选项卡将单独连接到服务器以启动服务器发送的事件,服务器将运行一个循环来完成请求。(如果每个用户打开5个选项卡,那么服务器将不得不启动5个不同的server-sent-event来响应!)

是否有一种方法可以添加某种逻辑来检查是否在客户端和服务器发送的脚本之间建立了连接,使用相同的连接而不是创建新的连接?

我认为这将是相同的想法使用WebSocket。然而,我使用WebSockets的问题是,每个用户必须使用服务器发送的事件进行身份验证,并且不确定这是否可能与WebSockets。当用户登录到应用程序,我生成一个sessionID和会话检查他们的ip/代理数据匹配之前,他们被允许使用网站。

如何将到服务器发送事件的连接最小化到每个用户1个?

在WebSocket服务器建立每个客户端的连接时,HTTP标头(以及cookie)是可用的。

然而,因为你没有使用WebSockets(还没有?),下一个最好的地方是你的客户端Javascript。

cookie在那里可用,除非cookie设置了HttpOnly标志。这将是你在多个浏览器选项卡中匹配用户的最可靠的方法。

浏览器用户代理字符串加上他们的IP地址是诱人的,但请记住,大多数家庭路由器使用NAT,许多住在一起的人倾向于在不同的计算机上使用相同的浏览器。

  • 每次连接限制为一个用户?是的。
  • 获得多个选项卡共享相同的SSE连接?是的,理论上。

扩展第一点:您提到您正在使用PHP会话。会话cookie将从您的每个选项卡发送,因此当第一个选项卡连接时,PHP脚本可以在会话(*)中设置一些内容,以表示您现在有一个SSE连接。当第二个选项卡连接时,PHP脚本将查找该会话变量,查看它,并返回一个错误代码。

关于第二点,这变成了一个标签间通信问题:第一个标签需要有一种方法来检测第二个标签的存在,并且必须有一种方法来与它通信,以便它可以转发它收到的SSE消息。我相信HTML5共享Web工作者可以实现这一点,我已经看到有人建议将其用于您描述的SSE用例,但我还没有看到一个工作示例。

*:记住在PHP脚本开始反馈SSE数据时使用session_write_close关闭会话,以便其他脚本可以使用该会话。

如果用户经过身份验证,那么您可能有一些用户记录。为用户记录添加会话ID,以便只响应该用户记录。

听起来你是在试图阻止具有相同身份验证细节的并发使用。在我看来,最好的方法是静默地忽略并发请求。

这是一个很好的问题,也是许多年后的回应,但是您的用例似乎有点奇怪

根据你下面的报价。我的用户使用多个选项卡来使用同一个应用程序。首先,他们希望在每个标签上看到相同的数据吗?我不明白为什么有这个必要?如果另一个标签是打开的,你要担心的标签是在焦点?

现在,如果他们打开多个选项卡来消费不同的信息,例如,一个金融应用程序有1。2.美国股市是英国股市。是亚洲股市。我能理解。但它也会排除你使用模糊处理。意思是,我更喜欢"关闭"连接。如果用户从选项卡中单击并将其报告给服务器以关闭()。

如果你不这样做,那么你应该控制你的超时,因为这会导致大量的内存泄漏。所以,要小心了。用户会做任何你让他们做的事情。

您可以采用的一种机制是活动blur会话。这意味着,如果用户点击了选项卡,模糊,您可以为预期的使用时间设置超时。如果屏幕是活动屏幕,那么您可以刷新连接并重新启动计时器。

所以,对我来说是的,从经过身份验证的用户那里获得一个选项卡并打开多个选项卡很容易。事实上,这是默认的。但这也是问题所在。

当你说:

是否有一种方法可以添加某种逻辑来检查是否在客户端和服务器发送的脚本之间建立了连接,使用相同的连接而不是创建新的连接?

如果将数据放到多个选项卡上是一个大问题,我会怎么做?对我来说,我喜欢"嘿,先生,你有一张账单"。这就是它的方法。

我将探索一种blur方法,该方法将从开放流中获取数据,并将其添加到redux或ngrx抽象或数据流抽象的浏览器会话中(两者都具有设置的复杂性)。

它的作用是说,"如果用户单击off标签"(非活动选项卡)则默认为来自传入事件流的备份数据流。因此,关闭主流,从流中输入生成的数据数组。运行在内存/redux/ngrx或单独的服务器,如RedisMongo

Auth0在一篇文章中有一个很好的例子。

处理服务器发送事件的连接恢复

在这个例子中,post人员解释说,可以通过跟踪发送的消息来处理丢失的连接和恢复,如果连接丢失,则向服务器发送信号。Last-Event-Id它将告诉用户发送的最后一条正确的消息,并将混乱的消息和新消息按顺序传递给用户。

现在,这个例子并不是你需要做的,但重点是一样的。保存消息并以不同的方式传递它们,这样当用户点击离开它们时,您就可以关闭其他选项卡。这样,您将在活动选项卡上拥有1 sse连接,而其他选项卡将从其他机制运行碳副本。保持连接质量,只有一个。

希望这能帮助到一些人。

我遇到了很多问题,因为我的用户使用多个浏览器的选项卡来使用同一个应用程序。

问题是,每个选项卡将单独连接到服务器以启动服务器发送的事件,服务器将运行一个循环来完成请求。(如果每个用户打开5个选项卡,那么服务器将不得不启动5个不同的server-sent-event来响应!)

是否有一种方法可以添加某种逻辑来检查是否在客户端和服务器发送的脚本之间建立了连接,使用相同的连接而不是创建新的连接?