使用 Redis 在 PHP 和 socket.io/node.js 之间进行通信

Posted

技术标签:

【中文标题】使用 Redis 在 PHP 和 socket.io/node.js 之间进行通信【英文标题】:Using Redis to communicate between PHP and socket.io/node.js 【发布时间】:2013-05-05 01:28:34 【问题描述】:

我有一个在 Apache 上构建和运行的 php 应用程序,使用 nginx 作为反向代理来提供静态资源。

我还安装了 Redis,我用它来存储每个用户活动流的活动 ID。活动被写入 mysql 数据库,然后 Redis 将活动 ID 推送到每个用户流中。当用户收到他/她的活动流时,应用首先从 Redis 中检索用户的活动 ID 列表,然后通过 MySQL IN() 查询获取实际活动数据。

这一切都很好,但是我想开始为这个设置添加实时功能。我希望能够将这些事件直接推送到用户浏览器并添加常规实时通知。

为此,我使用 socket.io 安装了 node.js。我已经正确启动并运行了 socket.io 服务器,并且客户端在页面加载时自动连接。

我正在努力理解如何从我的 PHP 应用程序中向 socket.io 发布消息。由于 PHP 和 node.js 无法直接通信,我的理解是我最好使用 Redis 作为中间人,因为我已经安装并启动并运行了它。但是我不知道该怎么做。

我需要的是描述从 PHP 发送通知到 Redis 然后到 socket.io 以便将其推送到相关客户端的过程(任何代码示例都会很有帮助)。

另外,我不明白 socket.io 如何知道要发送到哪个客户端。我将如何传递这些信息并保持一切同步?这甚至有必要吗?我是否需要将我的 PHP 会话存储在 Redis 中并让 socket.io 在用户连接时收集数据?还是有别的办法?

提前致谢。

请注意:我的 PHP SESSION 数据目前已保存到磁盘。

【问题讨论】:

如何在 redis 上拥有一个 pubsub 频道,并从你的 node.js 进程订阅它。然后,您的 PHP 将发布到 pubsub 以与节点通信。您可以为不同的客户提供单独的 pubsub 频道,并发布到您需要接触特定客户的任何频道。 @akonsu 这正是我最终所做的,谢谢。但是,我只设置了一个 pubsub 频道并将所有内容发布到该频道,只是为了将其放入 socket.io。在那里我计算出它应该去哪个特定的客户端等等......我会更好地为每个连接的客户端定义一个单独的 pubsub 通道吗?另外,如果你想写这个我会更详细地作为答案,我会标记它是正确的。 :) 老实说,我不知道为每个用户创建一个单独的频道。这取决于用户的数量。它可能无法扩展。但我绝对会记住拥有多个频道的可能性。有一天,当您的用户群增长时,您可能会拥有许多相关的 redis 实例并将您的频道分片给它们。 【参考方案1】:

您可以在 Redis 上设置发布订阅频道(请参阅http://redis.io/topics/pubsub)。然后从你的 node.js 进程订阅它。然后,您的 PHP 将发布到 pubsub 以与节点通信。您可以为不同的客户提供单独的 pubsub 渠道,并发布到您需要的任何渠道来联系您的特定客户。

【讨论】:

【参考方案2】:

Redis 不提供内置的 websocket 或 http 服务器,因此我们必须将其与 php 或 node.js 集成以传输通道数据。使用 Tweak 方法,我们可以使用 redis 的 predis php 库将 Redis 服务器与 php 连接,其中 php 会将数据推送到 Redis,而 socket.io 将跟踪推送到 Redis 服务器的新消息并将其发送回真实连接的用户时间。

https://github.com/u-day/tweak/

【讨论】:

以上是关于使用 Redis 在 PHP 和 socket.io/node.js 之间进行通信的主要内容,如果未能解决你的问题,请参考以下文章

php使用redis做缓存和使用redis保存session

redis在windows下安装和PHP中使用

使用 Redis 在 PHP 和 socket.io/node.js 之间进行通信

php关于redis的使用方法

Redis PHP连接操作

小贝_php+redis简单实例