消息的发送策略
持久化消息
默认情况下,生产者发送的消息是持久化的。消息发送到broker
之后,producer
会等待broker
对这条消息的处理情况的反馈。
这个过程性能和开销是比较大的,因为这个时候在broker
上不但要做消息的接收,同时还要根据自身的设置策略做持久化存储。为了提高持久化发送的性能,可以设置进行异步发送。
activeMQ
提供了异步发送的设置方法。
//创建连接工厂
ActiveMQConnectionFactory connectionFactory =
new ActiveMQConnectionFactory("tcp://localhost:61617");
connectionFactory.setUseAsyncSend(true);
//创建连接
Connection connection = connectionFactory.createConnection();
connection.start();
回执窗口大小设置
在同步模式下,消息发送端会等待broker
对消息的反馈,直到broker
接收消息。在异步模式下producer
是非阻塞的,是不知道broker
的反馈状态的,那么在broker
接收达到极限值后producer
还在持续的发消息,这样就会产生问题的。
通过设置回执窗口大小,当producer
端发送的消息达到这个设置值之后,会等待服务端的回执,这个时候在继续进行发送。设置方法如下:
connectionFactory.setProducerWindowSize(10240);
非持久化消息
通过设置消息的发送模式为非持久化
当消息到达broker
之后将不会对消息进行持久化操作,而是放到内存中。
message.setJMSDeliveryMode(DeliveryMode.NON_PERSISTENT);
非持久化消息模式下,默认就是异步发送模式。所以对于非持久化消息,就需要设置回执窗口大小。
另外如果需要对非持久化消息的每次发送的消息都获得broker
的回执的话,可以通过如下设置方法设置
connectionFactory.setAlwaysSyncSend(true);
consumer
获取消息是pull
还是broker
的主动push
默认情况下,mq服务器broker
采用异步方式向客户端主动推送消息(push)。也就是说broker
在向某个消费者会话推送消息后,不会等待消费者响应消息,直到消费者处理完消息以后,主动向broker
返回处理结果。
prefetchsize
:预取消息数量
broker
端一旦有消息,就主动按照默认设置的规则推送消息给当前活动的消费者。每次推送都有一定的数量限制,而这个数量就是prefetchsize
。
对于topic
和queue
两种模式下默认的prefetchsize
是不同的。
topic
模式下的prefetchsize
- 持久化消息:1000
- 非持久化消息:1000
queue
模式下的prefetchsize
- 持久化消息:100
- 非持久化消息:32766
假如prefetchsize=0
,此时对于consumer
来说,就是一个pull
模式
prefetchsize
的设置
Destination destination = session.createQueue("first-queue?customer.prefetchSize=100");
在创建目的地的时候,通过参数可以设置预取消息数量。
非事务模式下的消息确认
在非事务模式下,消费端和服务端在交换确认指令的时候还需要告诉broker
端ACK_TYPE
。broker
根据不同的ACK_TYPE
对消息做不同的处理。
ACK_TYPE
表示确认指令的类型。
REDELIVERED_ACK_TYPE
:当消费端消费消息发生异常的时候,会发送该指令。此时broker
会重新发送该消息到消费端。DELIVERED_ACK_TYPE
:表示消息已经接收,但是尚未处理结束。STANDARD_ACK_TYPE
:表示消息处理成功。