我试图找出实施队列系统的难度。我知道如何实现一个基本的队列,所以我将解释一下我所追求的一些背景:
我将实现一个将放置消息的队列,这将来自多个用户,消息将被安排在用户定义的时间发布(从UI的角度来看,允许多次出现,精确度为Minutes)将限制:“每分钟或每小时”发生,但ID仍然能够处理这个系统)。
这是我的问题所在: 最终我可能处于某种情况(也许不是)当前需要发布MANY消息的情况,我想要运行多个进程(多个脚本实例)来获取[x,10,25]数字一次来自队列的消息并处理它们。问题是:如何执行此操作以便每个实例处理唯一的消息(不处理已由另一个实例处理的内容)?我担心当前的连接,如何锁定记录,以及我可能没有想到的任何其他内容。
我将使用的技术是PHP和MySQL。我正在寻找上述的一些解决方案,我应该在我的搜索,真实世界的例子,想法,评论和想法中使用的术语?
谢谢大家!
我遇到的一个解决方案是使用Amazon Simple Queue Service ...它承诺独特的消息处理/锁定http://aws.amazon.com/sqs/
答案 0 :(得分:5)
好吧,我会这样做:
为消息制作表格并添加另外两个字段 - “PROCESS_ID”和“PROCESS_TIME”。这些将在后面解释。
为每个进程提供唯一的ID。他们可以在启动时生成它(如GUID),或者您可以自己分配它们(然后您可以更容易地将它们分开)。
当进程想要获取大量消息时,它会执行以下操作:
UPDATE messages SET process_id=$id, process_time=now() where process_id is null LIMIT 20
这将找到20条“免费”消息并“锁定”它们。然后它会找到它锁定的消息并处理它们。处理完每封邮件后,DELETE
即可。
UPDATE语句应该是非常原子的,特别是如果你使用InnoDB,它会自动将每个这样的语句包装在一个事务中。 MySQL应该关注那里的所有并发。
PROCESS_TIME字段是可选的,但您可以使用它来查看进程何时挂起。如果邮件被锁定的时间过长,您可以断定出现问题并进行调查。
答案 1 :(得分:1)
你可以解决问题。
而不是同时将事情排除在队列之外的问题。获得后立即发布所有信息。 但是使用规则发布它,直到某个时间才能看到它。以这种方式做事可以帮助您避免锁定/争用问题。
答案 2 :(得分:1)
查看Beanstalkd消息队列。有PHP客户端。 Beanstalkd的一个很好的功能(与例如dropr相反)是你可以延迟消息。也就是说,您可以将消息发布到队列,并且在X秒过去之前不会将消息传递给客户端。
Beanstalkd确实有一个很大的缺点:它是一个内存中的队列。这意味着如果它(或你的机器)崩溃,那么队列是空的并且内容丢失。持久性是为下一版beanstalkd计划的功能。
答案 3 :(得分:0)
一些在线解决方案:
我猜谷歌解决方案便宜得多(如果不使用太多,甚至可以免费)。
我一直在考虑在PHP / MYSQL中实现队列,并考虑使用: