ActiveMQ的消息事務
消息事務,是保證消息傳遞原子性的一個重要特性,和JDBC的事務特征類似。
一個事務性發送,其中一組消息要么能夠全部保證到達服務器,要么都不到達服務器。生產者,消費者與消息服務器都支持事務性。ActiveMQ得事務主要偏向在生產者得應用。
ActiveMQ消息事務流程圖:
原生jms事務發送(生產者的事務發送)
不加事務得情況:(程序沒有錯誤,10條消息會到達mq中)
不加事務得情況:(程序有錯誤,結果是發送成功3條,其余不成功---因為沒有加事務)
加事務得情況:(程序無錯誤)
1 @Autowired 2 private JmsMessagingTemplate jmsMessagingTemplate; 3 @Autowired 4 private JmsTemplate jmsTemplate; 5 @Value("${activemq.name}") 6 private String name; 7 8 public void sendMessageTx(){ 9 //獲取連接工廠 10 ConnectionFactory connectionFactory = jmsMessagingTemplate.getConnectionFactory(); 11 Session session = null; 12 try{ 13 //創建連接 14 Connection connection = connectionFactory.createConnection(); 15 //參數一:是否開啟消息事務 16 session = connection.createSession(true,Session.AUTO_ACKNOWLEDGE); 17 //創建生產者 18 MessageProducer producer = session.createProducer(session.createQueue(name)); 19 20 for(int i=1;i<=10;i++){ 21 TextMessage textMessage = session.createTextMessage("消息--"+i); 22 producer.send(textMessage); 23 } 24 25 //注意:一旦開啟事務發送,那么就必須使用commit方法進行事務提交,否則消息無法到達MQ服務器 26 session.commit(); 27 }catch(JMSException e){ 28 e.printStackTrace(); 29 //消息事務回滾 30 try{ 31 session.rollback(); 32 }catch(JMSException e1){ 33 e1.printStackTrace(); 34 } 35 36 } 37 }
加事務得情況:(程序有錯誤 結果一條都沒有成功發送,原因就是開啟了事務,事務的原子性導致的)
1 @Autowired 2 private JmsMessagingTemplate jmsMessagingTemplate; 3 @Autowired 4 private JmsTemplate jmsTemplate; 5 @Value("${activemq.name}") 6 private String name; 7 8 public void sendMessageTx(){ 9 //獲取連接工廠 10 ConnectionFactory connectionFactory = jmsMessagingTemplate.getConnectionFactory(); 11 Session session = null; 12 try{ 13 //創建連接 14 Connection connection = connectionFactory.createConnection(); 15 //參數一:是否開啟消息事務 16 session = connection.createSession(true,Session.AUTO_ACKNOWLEDGE); 17 //創建生產者 18 MessageProducer producer = session.createProducer(session.createQueue(name)); 19 20 for(int i=1;i<=10;i++){ 21 22 //模擬異常 23 if(i==4){ 24 int a = 10/0; 25 } 26 27 TextMessage textMessage = session.createTextMessage("消息--"+i); 28 producer.send(textMessage); 29 } 30 31 //注意:一旦開啟事務發送,那么就必須使用commit方法進行事務提交,否則消息無法到達MQ服務器 32 session.commit(); 33 }catch(JMSException e){ 34 e.printStackTrace(); 35 //消息事務回滾 36 try{ 37 session.rollback(); 38 }catch(JMSException e1){ 39 e1.printStackTrace(); 40 } 41 42 } 43 }
JMSTransactionManager(生產者的事務發送)
spring的JmsTransactionManager功能(這里不詳細介紹了)
消費者的事務接收
這里要注意:如果重發了6次之后,還沒有成功,那么會把該消息發送到一個死信隊列中(至於什么叫死信隊列在后面會提到)
ActiveMQ的消息確認機制
JMS消息只有在被確認之后,才認為已經被成功的消費了。消息的成功消費通常包含三個階段:客戶接收消息,客戶處理消息和消息被確認。在事務性會話中,當一個事務被提交的時候,確認自動發生。在非事務性會話中,消息何時被確認取決於創建會話時的應答模式(acknowledgement mode)。該參數有三個可選值:
注意:消息確認機制與事務機制是沖突的,只能選其中一種,所以演示消息確認前,先關閉事務。
參考:
黑馬程序員視頻:ActiveMQ部分的內容,若有侵權,請聯系我,立即刪除。
持續更新!!!