如何防止ActiveMQ优先级队列上的低优先级消息被饿死?

时间:2011-06-18 00:44:14

标签: java queue message-queue activemq priority-queue

我正在开发一个需要实现优先级队列的系统。我们有不同优先级的消息,我们需要根据优先级处理消息。目前,我们正在寻求使用ActiveMQ作为我们的排队技术,原因有很多,其中一个原因是支持优先级队列。

在ActiveMQ中使用优先级队列,处理饥饿的最佳方法是什么?具体而言,即使优先级较高的消息继续充斥队列,我们​​也需要确保即使是低优先级的消息也会被处理。 ActiveMQ有内置功能吗?或者,当消息老化时,我们是否需要构建自己的东西来提高优先级?

1 个答案:

答案 0 :(得分:4)

执行此操作的基本方法是在邮件变老时提高优先级

这样一小时前的低优先级消息优先于新的高优先级消息

public class Message implements Comparable<Message>{

    private final long time;//timestamp from creation (can be altered to insertion in queue) in millis the lower this value the older the message (and more important that it needs to be handled)
    private final int pr;//priority the higher the value the higher the priority

    /**
     * the offset that the priority brings currently set for 3 hours 
     *
     * meaning a message with pr==1 has equal priority than a message with pr==0 from 3 hours ago
     */
    private static final long SHIFT=3*60*60*1000; 

    public Message(int priority){
        this.pr=priority;
        this.time = System.currentTimeMillis();
    }

    //I'm assuming here the priority sorting is done with natural ordering
    public boolean compareTo(Message other){
        long th = this.time-this.pr*SHIFT;
        long ot = other.time-other.pr*SHIFT;
        if(th<ot)return 1;
        if(th>ot)return -1;
        return 0;
    }

}

正如评论中所指出的那样,几小时前来自低prio消息的洪水会暂时使新的高prio消息挨饿,而那些正常出来的消息将需要更复杂的方法


另一种方法是使用多个队列,每个队列对应一个优先级,并从低优先级队列中取出每个优先级队列中的几个队列

这个最后一种方法只对少量优先级真正可行,而我提供的第一种方法可以处理任意数量的优先级