WebSocket 推送数据库更新

Mik*_*378 5 architecture heroku websocket redis playframework-2.2

网络上大多数涉及 WebSocket 的文章都是关于内存聊天的。
我对不太即时的聊天感兴趣,这种聊天是持久的,就像博客帖子的评论一样。

我有一个由两台服务器组成的集群,处理客户端请求。
我想知道处理将数据库更新推送到相应客户端的最佳策略是什么。

当我使用 Heroku 来处理这个集群(由 2 个网络测功机组成)时,我显然阅读了本教程,旨在构建一个在所有客户端之间共享的聊天室。

它使用 Redis 来集中传入的消息;每个服务器侦听新消息以通过 websocket 连接传播到 Web 客户端。

我的用例的不同之处在于我有一个 Neo4j 数据库,将任何客户端写入的每条消息持久保存到其中。
我的目标是通知特定房间的每个客户,客户刚刚保留了新消息/评论。

使用与上面链接的教程类似的架构,如何仅过滤新消息以传播给用户?有没有一种简单有效的方法来告诉Redis:

“(WebSocket 说)当我的客户端启动 websocket 连接时,我会注意查询所有持久消息并将它们发送到客户端,但是我希望你(Redis)向我提供所有新消息,但我没有发送给客户,以便我能够提供它们。”

如何防止Redis在每次建立websocket连接时发布整个会话?这会导致重复,因为数据库查询此时已经提供了现有内容。

Yuv*_*dam 3

这实际上是一个非常常见的场景,其中包含三个组件:

  1. 无状态 Web 服务器集群,与所有客户端保持开放连接(显然,整个集群的负载均衡)
  2. 持久的主数据存储 - Neo4j 在您的情况下
  3. 用于跨通道(从而跨服务器集群)广播消息的消息/队列后端 - Redis

您的要求是新客户能够实时接收最近消息的初始提要以及任何后续消息。所有这些都在您的连接处理程序中实现。

本质上,您的(伪)代码应该如下所示:

class ConnectionHandler:

    redis = redis.get_connection()

    def on_init():
        self.send("hello, here are all the recent messages")
        recent_msgs = fetch_msgs_from_neo4j()
        self.send(recent_msgs)
        redis.add_listener(on_msg)
        self.send("now listening on new messages")

    def on_msg(msg):
        self.send("new message: ")
        self.send(msg)
Run Code Online (Sandbox Code Playgroud)

确切的实现实际上取决于您的环境,但这是一般流程。