一、ActiveMQ消息持久化
MQ消息中间件服务器和持久化的数据库服务器保证了高可用性。
ActiveMQ中,持久化是值对消息数据的持久化。在ActiveMQ中,默认的消息是保存在内存中的。当内存容量不足的时候,或ActiveMQ正常关闭的时候,会将内存中的未处理的消息持久化到磁盘中。具体的持久化策略是kahadb。如果使用JDBC作为持久化策略,则会将所有的需要持久化的消息保存到数据库中。
所有持久化配置都在conf/activemq.xml中配置,配置信息都在broker标签内部定义。
逻辑:
在发送者将消息发送出去后,消息中心首先将消息存储到本地数据文件、内存数据库或远程数据库等再试图将消息发送给接收者,成功则将消息从存储中删除,失败则继续尝试发送。消息中心启动后首先要检查指定的存储位置,若有未发送成功的消息,则需要把消息发送出去。
二、KahanDB
KahaDB是基于日志文件的持久性数据库,是自ActiveMQ 5.4以来的默认存储机制,可用于任何场景,提高了性能和恢能力,它是基于文件的本地数据库存储形式。它已针对快速持久性进行了优化。KahaDB使用较少的文件描述符,并提供比其前身AMQ消息存储更快的恢复。
在acticemq.xml中对broker标签下persistenceAdapter(持久化适配器)配置:
<persistenceAdapter> <kahaDB directory="${activemq.data}/kahadb"/> persistenceAdapter>
配置模板:
<broker brokerName="broker"> <persistenceAdapter> <kahaDB directory="activemq-data" journalMaxFileLength="32mb"/> persistenceAdapter> broker>
kahadb下:
消息存储使用一个事务日志和仅仅用一个索引文件来存储所有地址。
db-1.log、db-2.log、db-3.log,单数据文件已满后会依次创建,默认为32MB。当不在引用到该文件任何消息后,文件会被归档或者删除。
db-data为持久化的BTree索引文件执行db-x.log
db.free为当前db.data文件哪些页空闲
db.redo 为恢复db-data B-Tree索引
lock为数据锁
三、LevelDB
ActiveMQ的LevelDB方案是在5.9.0
版本开始引入,LevelDB持久性适配器使用LevelDB作为高性能的消息存储。它是一个基于文件的存储库,它使用了Google的LevelDB,将索引保存到包含消息的日志文件中。它经过优化,提供了比KahaDB更快的持久性。它类似于KahahDB,但是它没有使用自定义的b树实现来索引写前日志,而是使用基于LevelDB的索引.
四、JDBC消息存储
拷贝mysql的驱动包
修改activemq.xml
配置jdbcPersistenceAdapter
<persistenceAdapter> <jdbcPersistenceAdapter dataSource="#mysql-ds" createTablesOnStartup="true"/> persistenceAdapter>
createTablesOnStartup是否在启动时创建数据表,默认是true,一般第一次用时启用。
数据库连接配置
这个id需要和jdbcPersistenceAdapter一致
"mysql-ds" "driverClassName" "url" "username" "password" "poolPreparedStatements"
数据表
启动activemq后会自动生成三张表
Activemq_msgs(消息表)
Activemq_acks(订阅关系表)
如果是持久化topic,订阅者信息会保存在这个表。
queue测试
消费后:
点对点消费类型,一旦被消费就会从broker中删除
如果将DeliveryMode设为NON_PERSISTENT
textMessage.setJMSDeliveryMode(DeliveryMode.NON_PERSISTENT);
不会将消息保存到mysql中(实际保存在内存中)
Topic测试
启动消费者
启动生产者
五、JDBC Message store with ActiveMQ Journal
使用jdbc读写比较慢,可在中间加一个高速缓存Journal,提升了性能。
Journal可以减少写入DB的消息。
修改activemq.xml
<persistenceFactory> <journalPersistenceAdapterFactory journalLogFiles="4" journalLogFileSize="32768" useJournal="true" useQuickJournal="true" dataSource="#mysql-ds" dataDirectory="activemq-data"/>persistenceFactory>
重新启动
随意发一些消息,就会发现消息在不消费的情况下,等一段时间,数据库中才会有数据,并且在队列消费过后,数据库的消息也会一段时间后才删除。
而且在journal目录下会产生一些文件,这些文件就是一些持久化文件。文件在ActiveMQ安装目录的/bin/activemq-data/journal
中