技術乾貨:ActiveMQ面試題及答案

陝西優就業發表於2020-01-19

    新年將至, 陝西優就業小編為大家年後跳槽蓄力,技術面試題分享給技術黨。


      推薦閱讀

    【技術乾貨】 http://blog.itpub.net/69902581/viewspace-2672371/


    1、什麼是 ActiveMQ?

  activeMQ是一種開源的,實現了JMS1.1規範的,面向訊息(MOM)的中介軟體,為應用程式提供高效的、可擴充套件的、穩定的和安全的企業級訊息通訊。

  2、Activemq的瓶頸值

  根據網上一般評測文件上來看,每秒的訊息吞吐在2000以上, acticemq也可以叢集化部署,也是使用zookeeper來搭建。

  3、ActiveMQ伺服器當機怎麼辦?

  這得從ActiveMQ的儲存機制說起。在通常的情況下,非持久化訊息是儲存在記憶體中的,持久化訊息是儲存在檔案中的,它們的最大限制在配置檔案的節點中配置。

  但是,在非持久化訊息堆積到一定程度,記憶體告急的時候,ActiveMQ會將記憶體中的非持久化訊息寫入臨時檔案中,以騰出記憶體。雖然都儲存到了檔案裡,但它和持久化訊息的區別是,重啟後持久化訊息會從檔案中恢復,非持久化的臨時檔案會直接刪除。

  那如果檔案增大到達了配置中的最大限制的時候會發生什麼?我做了以下實驗:

  設定2G左右的持久化檔案限制,大量生產持久化訊息直到檔案達到最大限制,此時生產者阻塞,但消費者可正常連線並消費訊息,等訊息消費掉一部分,檔案刪除又騰出空間之後,生產者又可繼續傳送訊息,服務自動恢復正常。

  設定2G左右的臨時檔案限制,大量生產非持久化訊息並寫入臨時檔案,在達到最大限制時,生產者阻塞,消費者可正常連線但不能消費訊息,或者原本慢速消費的消費者,消費突然停止。整個系統可連線,但是無法提供服務,就這樣掛了。

  具體原因不詳,解決方案:儘量不要用非持久化訊息,非要用的話,將臨時檔案限制儘可能的調大。

  4、AcitveMQ的作用、原理?(生產者、消費者。p2p、訂閱實現流程)

  Activemq的作用就是系統之間進行通訊。當然可以使用其他方式進行系統間通訊,如果使用Activemq的話可以對系統之間的呼叫進行解耦,實現系統間的非同步通訊。原理就是生產者生產訊息,把訊息傳送給activemq。Activemq接收到訊息,然後檢視有多少個消費者,然後把訊息轉發給消費者,此過程中生產者無需參與。消費者接收到訊息後做相應的處理和生產者沒有任何關係

  5、activemq在專案中如何應用的

  Activemq在專案中主要是完成系統之間通訊,並且將系統之間的呼叫進行解耦。例如在新增、修改商品資訊後,需要將商品資訊同步到索引庫、同步快取中的資料以及生成靜態頁面一系列操作。

  在此場景下就可以使用activemq。一旦後臺對商品資訊進行修改後,就向activemq傳送一條訊息,然後透過activemq將訊息傳送給訊息的消費端,消費端接收到訊息可以進行相應的業務處理

  7、rabbitmq如何實現叢集高可用?

  叢集是保證服務可靠性的一種方式,同時可以透過水平擴充套件以提升訊息吞吐能力。RabbitMQ是用分散式程式設計語言erlang開發的,所以天生就支援叢集。接下來,將介紹RabbitMQ分散式訊息處理方式、叢集模式、節點型別,並動手搭建一個高可用叢集環境,最後透過java程式來驗證叢集的高可用性。

  RabbitMQ分散式的訊息處理方式有以下三種:

  (1)Clustering:不支援跨網段,各節點需執行同版本的Erlang和RabbitMQ,應用於同網段區域網。

  (2)Federation:允許單臺伺服器上的Exchange或Queue接收發布到另一臺伺服器上Exchange或Queue的訊息,應用於廣域網。

  (3)Shovel:與Federation類似,但工作在更低層次。

  RabbitMQ對網路延遲很敏感,在LAN環境建議使用clustering方式;在WAN環境中,則使用Federation或Shovel。我們平時說的RabbitMQ叢集,說的就是clustering方式,它是RabbitMQ內嵌的一種訊息處理方式,而Federation或Shovel則是以plugin形式存在。

  8、丟訊息怎麼辦?

  這得從java的java.net.SocketException異常說起。簡單點說就是當網路傳送方傳送一堆資料,然後呼叫close關閉連線之後。這些傳送的資料都在接收者的快取裡,接收者如果呼叫read方法仍舊能從快取中讀取這些資料,儘管對方已經關閉了連線。

  但是當接收者嘗試傳送資料時,由於此時連線已關閉,所以會發生異常,這個很好理解。不過需要注意的是,當發生SocketException後,原本快取區中資料也作廢了,此時接收者再次呼叫read方法去讀取快取中的資料,就會報Software caused connection abort: recv failed錯誤。

  透過抓包得知,ActiveMQ會每隔10秒傳送一個心跳包,這個心跳包是伺服器傳送給客戶端的,用來判斷客戶端死沒死。如果你看過上面第一條,就會知道非持久化訊息堆積到一定程度會寫到檔案裡,這個寫的過程會阻塞所有動作,而且會持續20到30秒,並且隨著記憶體的增大而增大。

  當客戶端發完訊息呼叫connection.close()時,會期待伺服器對於關閉連線的回答,如果超過15秒沒回答就直接呼叫socket層的close關閉tcp連線了。這時客戶端發出的訊息其實還在伺服器的快取裡等待處理,不過由於伺服器心跳包的設定,導致發生了java.net.SocketException異常,把快取裡的資料作廢了,沒處理的訊息全部丟失。

  解決方案:用持久化訊息,或者非持久化訊息及時處理不要堆積,或者啟動事務,啟動事務後,commit()方法會負責任的等待伺服器的返回,也就不會關閉連線導致訊息丟失了。


來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/69902581/viewspace-2673947/,如需轉載,請註明出處,否則將追究法律責任。

相關文章