ActiveMQ 中的 AMQP 1.0 支持 - 无法设置预取



我们正在尝试在ActiveMQ 5.9.1之上构建一个作业队列系统。我们在activemq中使用AMQP 1.0支持,目前客户端代码使用qpid jms库。

对于作业队列系统而言,将预取设置为1是至关重要的-我们希望作业工人一次只能获得一个任务,竞争消费者模式。qpid库使用如下的连接工厂定义来支持这一点:

connectionfactory.activemq-amqp-manager = amqp://{user}:{password}@{hostname}:{port}?clientid=job-manager&remote-host=default&max-prefetch=1

然而,ActiveMQ似乎完全忽略了这一点,消费者在ActiveMQ管理控制台上显示为预取100。

进一步挖掘,我找到了:org.apache.activemq.transport.amqp.AmqpProtocolConverter的源代码

包括以下行:

  consumerInfo.setPrefetchSize(100);

这是否意味着AMQP 1.0协议的ActiveMQ支持为所有客户端硬连接了100的预取值?显然,这是非常错误的。我们有什么选择?我们可以切换到纯JMS客户机,但会失去语言互操作性。或者我们可以切换到RabbitMQ,这意味着引入另一个产品来支持(ActiveMQ已经在其他地方使用了)。

您是否实际做了任何测试,以查看预取为1的消费者是否按预期工作?

ActiveMQ的内部不是基于AMQP,所以即使一个AMQP消费者是连接的,事情也不会总是像你想要的那样出现。AMQP客户端连接的ActiveMQ内部消费者默认为100,但是向客户端的消息调度仍然受到远程端设置的当前流窗口的限制。如果QPid客户端在设置预取值时将链接信用限制为1,则代理将只发送一条消息。

这里唯一需要注意的是,每个订阅最初都可以在代理端预取,但最终会在消费者端预取,因为随着更多消费者的加入,代理将进行轮循调度。

ActiveMQ中对AMQP的支持还在不断成熟,所以欢迎您深入了解并尝试改进它。

最新更新