使用 EventMachine 的 Rails 应用程序是不是可以进行长轮询?
Posted
技术标签:
【中文标题】使用 EventMachine 的 Rails 应用程序是不是可以进行长轮询?【英文标题】:Is long polling possible with a Rails application using EventMachine?使用 EventMachine 的 Rails 应用程序是否可以进行长轮询? 【发布时间】:2012-01-03 18:56:12 【问题描述】:我正在 Rails 3.1 中编写一个简单的聊天室应用程序 - 用于学习目的。 对于初学者,我拥有所有需要的模型(消息、用户、房间等),而且一切都很好。 客户端每分钟轮询一次服务器(例如),如果有新消息,则获取新消息。
我想将简单轮询更改为长轮询,但不知道这是否可以在同一个应用程序中完成,或者我是否必须为长轮询创建一些其他推送服务器。
我阅读了很多有关 EventMachine 的内容,并将我的 rails 应用程序更改为使用它,因为我想将 EventMachine 用于事件驱动机制。我认为 EventMachine 频道会为此派上用场。 客户端会在聊天室中连接并等待消息,并且只有在消息被发送到聊天室时才会收到消息。
我不知道如何在所有客户端连接之间共享 EventMachine::Channel 实例。 这种方法是否可行,还是我走错了路?
如果可能的话,我想要一个可以作为托管在 Heroku 上的单个 Rails 应用程序运行的解决方案。
【问题讨论】:
我不是事件机器方面的专家,但我认为这是可能的。而且您不会在客户端之间共享通道,但每个客户端都有一个通道,并且您需要在 EM 之上构建一些东西以在不同用户之间发送消息。 是的,假设我为每个客户都有一个频道。我在哪里可以存储所有这些通道实例,以便可以从其他人发送消息时调用的控制器访问它? 【参考方案1】:是的,当然。我刚刚使用事件机编写了一个演示。我的情况是玩家在地图上走来走去,其他玩家应该能够看到它。 演示如下:
客户端建立连接,报告自己的坐标(随机生成)
有一个数组保存了每个客户端的所有坐标
当客户端移动时,它会将其新坐标发送到服务器。然后服务器找到他附近的人(从数组中),并将新坐标推送给这些客户端。
我对近 5000 个客户进行了测试,每秒有 20-30 名玩家移动它的位置。并且服务器进程只占用不到 100M 的内存和 50%-60% 的 cpu 使用率(在单核上)。
在你的情况下,我想你也应该试试 faye。它基于事件机器,是聊天室等事物的适当解决方案。
【讨论】:
【参考方案2】:扩展我在评论中提到的内容,查看此 blog 帖子,该帖子解释了如何使用 EM 创建基于文本的聊天应用程序,并使用 AMQP 将消息广播给其他用户。
我认为您可能也可以这样做或使用内存队列中的一些来共享消息,这绝对应该在 heroku 上工作,因为您不依赖于外部服务,例如 RabbitMQ。 这是关于不同队列框架的一个很好的讨论:ActiveMQ or RabbitMQ or ZeroMQ or
【讨论】:
【参考方案3】:Rails 将在版本 4 中添加流式传输。 现在,您可以像this 示例中那样使用 Sinatra 和 Redis 的 Pub/Sub 功能作为后端进行流式传输(长轮询)。您必须添加另一个操作来处理用户发送的消息,使用 PUBLISH 命令将它们添加到 Redis 中。你应该使用像 Thin 或 Puma 这样的事件服务器。
【讨论】:
以上是关于使用 EventMachine 的 Rails 应用程序是不是可以进行长轮询?的主要内容,如果未能解决你的问题,请参考以下文章
Rails eventmachine 未初始化 evma_install_oneshot_timer
Ruby on Rails Eventmachine 段错误
Rails - 无法运行应用程序:无法加载 EventMachine C 扩展;