當前各種 RPC 中間件技術已經廣泛應用於各個領域。其中,服務器之間消息通訊這種功能廣泛應用於這些中間件中,於是,將這種面向消息的中間件( Message Oriented Middleware , MOM )抽象出來,形成通用的消息中間件,成為業內主流。目前消息中間件的標准主要有: JMS 和 AMQP 。實現則是百花齊放。
消息中間件從功能上需要解決以下問題:
1. 同步或異步的消息傳輸,尤其是異步的消息傳輸
同步發送消息是發送消息后,阻塞等待消息是否發送成功的回饋,如果設置有超時時間,則超時后跳出阻塞狀態。
異步發送消息是發送消息后,不阻塞立即執行其他操作。如果關心消息是否發送成功,則可以通過回調函數(Java 中的 Listener )處理消息是否成功。
2. 消息的安全性,消息中間件對持久的支持
在分布式系統中,消息從發送到接收,環節非常多,沒有任何一個環節是安全的,而任何環節出了問題,都會導致丟消息。當有需求是,我們必須保證在不是絕對安全的多環節里,完成消息安全的傳輸。這其中,消息中間的持久是非常重要的。
3. 消息的重發性
如果使用的系統保證了冪等性,則對此沒有要求。否則,有些場景需要保證消息不重發。在既要保證消息安全,又要保證消息不重發,是非常困難的。目前業內還沒有人能解決此問題。
目前,在有消息重發的情況下,使用的系統都是使用狀態機保證了系統對消息的冪等性。
4. 消息的順序性
如果使用的系統有要求,則有可能需要保證消息的順序。在大規模分布式不可靠環境下,在保證消息傳輸高效和消息安全的情況下,要解決此問題,也是非常困難的。
如果只是小規模的系統,對性能要求不高,可以以服務器時間為准,使用排隊隊列即可解決。
如果以發送端時間為准,並且保持順序的消息由此一個發送端發送,則使用消息序號即可解決。
另外,有些系統只需要滿足局部的消息順序性,在排序消息數量不大的情況下,可以使用多條排序消息一次性發送解決。
5. 消息傳輸模型:點對點的傳輸消息( PTP ),訂閱 / 發布模型( Pub/Sub )
PTP ,就是你在消息方設置消息接收者的唯一標識符,然后,消息發送方和消息接受方建立一一對應的關系。消息發送方發送所有的消息都被消息接收方接收。
Pub/Sub ,就是消息發送方和消息接收方都確定自己的發送和接收消息的標簽(或者你可以理解為組 GroupID),所有有這個標簽的消息,訂閱了這個標簽的消息接收方一定能接收到。
JMS ( Java 消息服務, Java Message Service )是專用於 J2EE 的一種消息中間件規范。它主要做了接口上的規范,消息傳輸模型和消息類型的規范,並沒有給予實現。同樣,它也完全沒有給出服務器端的架構,你甚至可以不使用服務器直接在客戶端之間傳輸消息(雖然可能最終結果只是一個玩具)。http://java.sun.com/products/jms/docs.html 。 JMS 也沒有規定消息的順序,安全,重發等特性。
AMQP (高級消息隊列協議, The Advanced Message Queuing Protocol )是一種和語言無關的,在金融行業使用的新興消息中間件,目前成為消息中間件圈內關注的焦點。與 JMS 規范了 API 不同,它是一個異步消息傳遞所使用的應用層協議規范。 AMQP 的原始用途只是為金融界提供一個可以彼此協作的消息協議,而現在的目標則是為通用消息隊列架構提供通用構建工具。 http://www.amqp.org/