【问题标题】:Artemis durable subscription message storageArtemis 持久订阅消息存储
【发布时间】:2019-07-30 22:21:15
【问题描述】:

我正在尝试了解持久订阅在 ActiveMQ Artemis 中的工作原理。目前我最大的问题是关于存储。

我想知道消息是否重复,这意味着对于每个消费者来说,消息都存储在磁盘上,或者消息是否存储在一个地方,消费者只知道他们断开连接并需要恢复的消息。

从我的测试中,我可以看到:对于固定的消息大小和发布的消息数量,磁盘上占用的空间是相同的,无论我有 1,2 还是 3 个持久订阅。我负责断开它们以便存储消息,别担心。这会让我认为队列只知道消费者回来时需要开始消费的消息的索引。

但相反,我使用 iostat cmd 检查了每秒写入字节数,并且我拥有的持久订阅队列越多,这个统计数据增长得越多。这意味着消息是重复的。

你们有没有更多的信息,甚至是负责这个的源代码。

【问题讨论】:

    标签: activemq-artemis durable-subscription


    【解决方案1】:

    默认情况下,ActiveMQ Artemis 会将持久消息存储在一组称为“日志”的本地文件中。在多个队列具有相同消息的情况下(例如,在同一 JMS 主题上的多个持久订阅的情况下)实际消息数据只存储一次,并且每个队列都获得一个“引用”到那个消息。多次存储完全相同的消息数据效率会非常低。

    然而,值得注意的是,ActiveMQ Artemis 日志文件在创建时初始化为零,这意味着即使是“空”日志也会占用磁盘空间。因此,当消息存储在日志中时,它们占用的磁盘空间量不会改变。现有的零将简单地被消息数据覆盖。

    你可以找到ActiveMQ Artemis on GitHub的源代码。

    如果您想查看此行为的证据,可以使用artemis data print 命令。此命令以人类可读的格式打印来自日志的原始记录。如果您在名为exampleTopic 的JMS 主题上分别使用durable-client1durable-client2 的客户端ID 和subscriber-1subscriber-2 的订阅名称有2 个持久订阅,并且您发送一条消息,您最终会收到一条消息地址、2 个队列、1 条实际消息和 2 条日志中的引用。您会在data print 命令输出中看到类似的内容:

    ********************************************
    B I N D I N G S  J O U R N A L
    ********************************************
    ...
    
    ### Surviving Records Summary ###
    ...
    recordID=2;userRecordType=44;isUpdate=false;compactCount=0;PersistentAddressBindingEncoding [id=2, name=exampleTopic, routingTypes={MULTICAST}, autoCreated=false]
    recordID=18;userRecordType=21;isUpdate=false;compactCount=0;PersistentQueueBindingEncoding [id=18, name=durable-client1.subscriber-1, address=exampleTopic, filterString=null, user=null, autoCreated=false, maxConsumers=-1, purgeOnNoConsumers=false, exclusive=false, lastValue=false, lastValueKey=null, nonDestructive=false, consumersBeforeDispatch=0, delayBeforeDispatch=-1, routingType=0, configurationManaged=false, groupRebalance=false, groupBuckets=-1, groupFirstKey=null, autoDelete=false, autoDeleteDelay=0, autoDeleteMessageCount=0]
    recordID=23;userRecordType=21;isUpdate=false;compactCount=0;PersistentQueueBindingEncoding [id=23, name=durable-client1.subscriber-2, address=exampleTopic, filterString=null, user=null, autoCreated=false, maxConsumers=-1, purgeOnNoConsumers=false, exclusive=false, lastValue=false, lastValueKey=null, nonDestructive=false, consumersBeforeDispatch=0, delayBeforeDispatch=-1, routingType=0, configurationManaged=false, groupRebalance=false, groupBuckets=-1, groupFirstKey=null, autoDelete=false, autoDeleteDelay=0, autoDeleteMessageCount=0]
    
    ...
    
    ********************************************
    M E S S A G E S   J O U R N A L
    ********************************************
    ...
    
    ### Surviving Records Summary ###
    recordID=27;userRecordType=45;isUpdate=false;compactCount=0;Message(messageID=27;userMessageID=41705395-b2d1-11e9-91f9-a0afbd82eaba;msg=CoreMessage[messageID=27,durable=true,userID=41705395-b2d1-11e9-91f9-a0afbd82eaba,priority=4, timestamp=Tue Jul 30 08:52:22 CDT 2019,expiration=0, durable=true, address=exampleTopic,size=232,properties=TypedProperties[__AMQ_CID=durable-client1,_AMQ_ROUTING_TYPE=0]]@454305524
    recordID=27;userRecordType=32;isUpdate=true;compactCount=0;AddRef;QueueEncoding [queueID=18]
    recordID=27;userRecordType=32;isUpdate=true;compactCount=0;AddRef;QueueEncoding [queueID=23]
    ...
    

    【讨论】:

    • 感谢源代码,我已经克隆了它,但我很难找到您所描述的行为在代码中的处理位置。如果你知道我在哪里可以得到这种行为的证明,那真是太棒了。非常感谢您的回答和编辑,您帮了很多忙。
    • 感谢您的回答。最后一个问题,Artemis 是否回到了非隔离队列日志?在最新的 activemq 中,队列有单独的文件夹。 @贾斯汀伯特伦
    • 我不明白你的问题。由于这个问题已经得到回答,因此也许可以在这里创建一个新问题而不是评论。
    猜你喜欢
    • 2019-09-30
    • 2018-09-22
    • 2017-11-08
    • 1970-01-01
    • 2020-11-18
    • 2015-06-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多