我正在尝试通过将复杂的数据库任务发送到RabbitMQ队列以由工作人员dyno处理来简化我的应用程序,以减少服务器负载。
对于INSERT
和UPDATE
来说,这相对简单。但是,我要发送几个密集的SELECT
到队列。但是,我遇到的问题是,准备就绪后如何将响应返回给用户的浏览器。
我知道我应该将响应发送到第二个队列,并在客户端的浏览器中创建使用者。但是,这样做会遇到一些实际问题,例如如何从队列中选择正确的响应,而不是简单地选择下一个响应(例如,如果两个人同时在页面上)。
有人有经验或建议吗?
谢谢
答案 0 :(得分:1)
RabbitMQ网站上有a tutorial on building a request-response "RPC" flow,听起来像是您所追求的。
正如您所说,单个“响应”队列将不起作用,因为您无法选择从队列中取出哪些项目,因此可以将它们全部按顺序进行。相反,技巧是为每个客户端创建一个单独的响应队列(或者,对于最简单的实现,为每个请求创建一个响应队列)。
您可以通过声明“匿名”队列来实现此目的,该队列并不是真正的匿名,RabbitMQ为您选择了它的名称。然后,您可以将该名称作为请求的一部分发送(通常在AMQP消息的reply_to
标头中),以便另一端的工作人员知道将响应发送到哪里。在php-amqplib中,如下所示:
list($reply_queue_name, ,) = $channel->queue_declare("", false, false, true, false);
注意:
queue_declare
调用返回一个数组,其中包含队列的名称和状态;我们只需要名称,因此我们使用list()
构造丢弃了数组的其余部分。true
,以声明队列为“独占”;这意味着该连接结束后,队列将被清理。答案 1 :(得分:0)
最后,我使用了不同于@IMSoP描述的方法。我很想听听关于哪种方法更有效或更有效的看法。
在排队的任务结束时,JSON响应被推送到Redis存储中(键是唯一的用户ID,值是JSON响应)。在浏览器中,AJAX用于每两秒钟运行一个PHP文件,该文件检查Redis存储库是否具有与用户ID匹配的密钥。找到后,它将值返回给浏览器,然后删除Redis上的key => value对。