1.什麼是MQ,有什麼用?java
MQ 是message queue ,消息隊列,也叫消息中間件,遵照JMS(java message service)規範的一種軟件。(同時還有另外一個叫AMQP的應用層協議,語言無關性不受產品 語言等限制,rabbitMQ支持這個 )spring
是相似於數據庫同樣須要獨立部署在服務器上的一種應用,提供接口給其餘系統調用。數據庫
主要用於各個系統之間通訊的解耦。安全
舉例:服務器
好比登錄系統,在登錄以後須要調用短信系統給用戶發短信說已經登錄,同時還須要調用日誌系統記錄登錄日誌,須要調用積分系統對登錄簽到的積分進行增長 等等等。session
這種狀況下,登錄系統和日誌系統,短信系統,積分系統等等 強耦合,其中存在可能調用失敗,信息丟失等風險,同時會提升系統複雜度。併發
好比說登錄以後調用日誌系統失敗,那麼該次登錄的日誌信息就會丟失,沒法再找回。異步
並且順序執行,會致使登錄系統運行效率低。tcp
那麼若是使用消息中間件,登錄以後只須要將任務推入到消息隊列中,就不用去管了。其餘系統則從隊列中去獲取任務。大數據
實現解耦和異步調用 (異步是相對於同步而言,同步是就等待,當系統執行某個任務的時候,必定要等到該任務結束,系統纔會繼續往下執行,異步則不等待。)
同時還有能夠實現橫向拓展 安全可靠優勢
2.常見MQ的類型
activeMQ 對java支持良好,缺點是對其餘語言支持不夠友好,適合中小企業系統
rabbitMQ 對java支持良好,對其餘語言也支持良好,跨平臺,語言無關
kaffka 日誌消息中間件 支持大數據場景
3.JMS規範
MQ實現參照了jms規範,(規範就是一種約定)
該規範中包括
提供者:實現jms規範的中間件服務器
客戶端:發送或者接受消息的應用程序
生產者/發佈者:建立併發送消息的客戶端
消費者/訂閱者:接受並處理消息的客戶端
消息:應用程序之間傳遞的內容
消息模式:在客戶端之間傳遞消息的方式,jms中定義了主題和隊列兩種模式
主題模式:
假如發佈者發佈了100條消息,那麼若是有n個訂閱者,每一個訂閱者均可以獲取到100條消息。即訂閱者能夠獲取到全部的消息(但若是訂閱是在主題發佈消息以後,則獲取不到任何消息,只能獲取到訂閱時間以後主題的發佈的消息,好比說A訂閱了B, B發佈了消息,C再訂閱了B,那麼只有a可以獲取到消息,C不能,由於它的訂閱行爲發生在B發佈消息以後)
隊列模式:
假如生產者發送了100條消息,若是有n個消費者,那麼每一個訂閱者加起來獲取到的消息總數是100。
沒有時間上限制。只要隊列中有消息,消費者能夠任意時間去取消息,一個消息只能被一個消費者消費。
4.jms約定的接口
ConnectionFactory 獲取與MQ服務鏈接的工廠類
Connection 與MQ服務的鏈接, 由ConnectionFactory 建立
Session 會MQ服務的會話 由Connection 建立
MessageProducer 消息生產者,由Session 建立
MessageConsumer 消息消費者 由Session建立
Message 消息,由Session建立
Desination 消息的目的地
5.原生實際代碼例子
一.原生mq用法 隊列, 建立生產者消費者模式
生產者發送消息
------------------------
//1.建立connectionFactory 與mq服務器進行鏈接
ConnectionFactory connectionFactory=new
XXMQConnectionFactory(url) ; //XX 爲該mq的實現 好比activeMQ rabbitMQ等
// url爲服務器地址 tcp格式 好比 tcp://xxxx:xxx
//2.建立Connection
Connection connection=connectionFactory.createConnection();
//3.啓動鏈接
connection,start();
//4.建立會話
Session session=connection.createSession(XXX); //xx爲該session的建立時候的參數 好比設定事務,模式等等,具體依據不一樣的實現形式
//5.建立一個目標
Destination destination=session.createQueue(queueName);
//6.建立一個生產者
MessageProducer producer=session.createProducer(destination);
//7.建立消息
TextMessage textMessage=session.createTextMessage("text");
//8.發送消息
producer.send(textMessage);
//9.關閉鏈接
connection.close();
----------------
消費者獲取消息
//1.建立connectionFactory 與mq服務器進行鏈接
ConnectionFactory connectionFactory=new
XXMQConnectionFactory(url) ; //XX 爲該mq的實現 好比activeMQ rabbitMQ等
// url爲服務器地址 tcp格式 好比 tcp://xxxx:xxx
//2.建立Connection
Connection connection=connectionFactory.createConnection();
//3.啓動鏈接
connection,start();
//4.建立會話
Session session=connection.createSession(XXX); //xx爲該session的建立時候的參數 好比設定事務,模式等等,具體依據不一樣的實現形式
//5.建立一個目標
Destination destination=session.createQueue(queueName);
//6.建立一個消費者
MessageConsumer consumer=session.createConsumer(destination);
//7.建立一個監聽器
consumer.setMessageListener(
new MessageListener(){
public void onMessage(Message message){
TextMessage textMessage=(TextMessage)message;
//8.獲取消息
textMessage.getText();
}});
//9.關閉鏈接
connection.close();
二.原生mq用法 主題, 建立發佈者 訂閱者模式
發佈者----
//1.建立connectionFactory 與mq服務器進行鏈接
ConnectionFactory connectionFactory=new
XXMQConnectionFactory(url) ; //XX 爲該mq的實現 好比activeMQ rabbitMQ等
// url爲服務器地址 tcp格式 好比 tcp://xxxx:xxx
//2.建立Connection
Connection connection=connectionFactory.createConnection();
//3.啓動鏈接
connection,start();
//4.建立會話
Session session=connection.createSession(XXX); //xx爲該session的建立時候的參數 好比設定事務,模式等等,具體依據不一樣的實現形式
//5.建立一個目標
Destination destination=session.createTopic(topicName);
//6.建立一個生產者
MessageProducer producer=session.createProducer(destination);
//7.建立消息
TextMessage textMessage=session.createTextMessage("text");
//8.發送消息
producer.send(textMessage);
//9.關閉鏈接
connection.close();
---訂閱者
//1.建立connectionFactory 與mq服務器進行鏈接
ConnectionFactory connectionFactory=new
XXMQConnectionFactory(url) ; //XX 爲該mq的實現 好比activeMQ rabbitMQ等
// url爲服務器地址 tcp格式 好比 tcp://xxxx:xxx
//2.建立Connection
Connection connection=connectionFactory.createConnection();
//3.啓動鏈接
connection,start();
//4.建立會話
Session session=connection.createSession(XXX); //xx爲該session的建立時候的參數 好比設定事務,模式等等,具體依據不一樣的實現形式
//5.建立一個目標
Destination destination=session.createTopic(topicName);
//6.建立一個消費者
MessageConsumer consumer=session.createConsumer(destination);
//7.建立一個監聽器
consumer.setMessageListener(
new MessageListener(){
public void onMessage(Message message){
TextMessage textMessage=(TextMessage)message;
//8.獲取消息
textMessage.getText();
}});
//9.關閉鏈接
connection.close();
6.spring集成下的代碼例子
ConnectionFactory用於管理鏈接的鏈接工廠 這個是
spring提供地鏈接池,spring提供了SingleConnectionFactory和
CachingConnectionFactory
JmsTemplate用於發送和接受消息的模板類,spring提供的 只要注入這個bean,既能夠
用jmsTempalate方便的操做jms 不須要像以前那樣寫一堆重複代碼
這個是線程安全的
MessageListerner 消息監聽器,實現了一個onMessage方法,該方法只接收一個Message參數
發送消息的方法
@Autowired JmsTemplate jmsTemplate; @Autowired Destination destination; jmsTemplate.send(destination,new MessgaeCreator(){ public Message createMessage(Session session) { TextMessage textMessage=session.createTextMessage("message"); return textMessage; }});
JmsTemplate實際上就是作了一層封裝而已 簡化了用法 ,能夠參考裏面的源代碼
---------------------
做者:laixiaoxing
來源:CSDN
原文:https://blog.csdn.net/qq_20009015/article/details/81409346