4.18.2. 环队列故障排除
本节介绍了环队列的行为与其配置不同的情况。
in-delivery 消息和回滚
当消息传送到消费者时,消息处于"在节点间的"状态,其中消息在技术上不再是队列中,但尚未被确认。消息会一直处于 in-delivery 状态,直到消费者确认。处于 in-delivery 状态的消息无法从环队列中删除。
因为代理无法删除 in-delivery 消息,所以客户端可以向环队列发送比环大小配置更多的消息。例如,请考虑这种情况:
-
制作者将三个消息发送到配置了
ring-size="3"
的环队列。 所有消息都会立即分配给消费者。
此时,
messageCount
=3
和 deliverCount
=3
。制作者将另一条消息发送到队列。然后,消息被分配到消费者。
现在,
MessageCount
=4
和deliverCount
=4
。4
的消息计数大于配置的环形大小为3
。但是,代理会被视为允许这种情况,因为它无法从队列中删除发送的消息。现在,假设使用者已关闭,且未被确认任何消息。
在这种情况下,四个正在发送中,未确认的消息将被取消回代理,并按照它们使用的相反顺序添加到队列的头位。此操作会使队列超过配置的环形大小。由于环队列优先选择队列用于通过头上消息的尾部消息,因此队列会丢弃制作者发送的第一个消息,因为这是最后一个消息已重新添加到队列的头条。事务或核心会话回滚会采用同样的方式处理。
如果您直接使用核心客户端,或者使用 AMQ Core Protocol JMS 客户端,您可以通过减少 consumerWindowSize
参数的值(1024 * 1024 字节)来最小化交付中的消息数量。
调度的消息
当计划的消息发送到队列时,不会立即将消息添加到队列的尾部,如普通消息。相反,代理将调度的消息保存在中间缓冲区中,并根据消息的详细信息,将消息传送到队列的头头。但是,调度的消息仍然反映在队列的消息计数中。与 in-delivery 消息一样,此行为可能会使得代理不强制实施环队列大小。例如,请考虑这种情况:
在 12:00 时,制作者将消息
A
发送到配置了ring-size
="3 的环队列。该消息被调度为 12:05。此时,Message
Count
=1
和scheduledCount
=1
。在 12:01 上,生产者将消息
B
发送到同一个环队列。现在,
MessageCount
=2
和scheduledCount
=1
。在 12:02,生产者将消息
C
发送到同一个环队列。现在,
MessageCount
=3
和scheduledCount
=1
。在 12:03,生产者将消息
D
发送到同一个环队列。现在,
MessageCount
=4
和scheduledCount
=1
。队列的消息计数现在为
4
,它 大于 配置的环形大小为3
。但是,尚未在队列(即,它位于代理中并计划放置在队列中)上的消息。在预定的 12:05 交付时间,代理会将消息放在队列的头部。但是,由于环队列已达到其配置的大小,调度的消息A
会立即被删除。
paged 信息
与发送中的消息和消息类似,页面消息不计到由代理实施的环队列大小,因为消息实际是在地址级别上的分页,而不是队列级别。页面化消息在技术上不是队列的 messageCount 值,但它反映在队列的 messageCount
值中。
建议您不要将分页用于带有环队列的地址。相反,请确保整个地址可适应内存。或者,将 address-full-policy
参数设置为 DROP
,BLOCK
或 FAIL
值。
其他资源
- 当您配置被动地址时,代理会创建环队列的内部实例。要了解更多信息,请参阅 第 4.19 节 “配置被动地址”。